Actionmailer
1.Actionmailer
メールの送信やメール本文の解析を行うActionMailerパッケージが標準装備されています。これを使ってSMTPやPOP3と簡単に遣り取りすることができます。ここでは簡単なメーラを作ってみましょう。
1-1.プロジェクトの生成
(1) プロジェクトAppli010を生成する
(2) 日本語環境の設定
(3) データベースの作成
1-2.テーブルpageの作成
(1) モデルの作成
NetBeansで[生成..]を選択します
ジェネレータ(G):model
引数(A):Page
exists app/models/
exists test/unit/
exists test/fixtures/
create app/models/page.rb
create test/unit/page_test.rb
create test/fixtures/pages.yml
create db/migrate
create db/migrate/20100210000356_create_pages.rb
(2) マイグレーションファイルの修正
class CreatePages < ActiveRecord::Migration
def self.up
create_table :pages do |t|
t.column :address, :string
t.timestamps
end
enddef self.down
drop_table :pages
end
end
(3) マイグレーションファイルの実行
NetBeansで[データベースマイグレーション]→[現在のバージョンへ]を選択します。
(in D:/Rails_Projects/Appli010)
== CreatePages: migrating ====================================================
-- create_table(:pages)
-> 0.1090s
== CreatePages: migrated (0.1090s) ===========================================
1-3.テーブルemailの作成
(1) モデルの作成
NetBeansで[生成]を選択します。
ジェネレータ(G):model
引数(A):Email
exists app/models/
exists test/unit/
exists test/fixtures/
create app/models/email.rb
create test/unit/email_test.rb
create test/fixtures/emails.yml
exists db/migrate
create db/migrate/20100210000929_create_emails.rb
(2) マイグレーションファイルの修正
class CreateEmails < ActiveRecord::Migration
def self.up
create_table :emails do |t|
t.column :page_id, :integer
t.column :subject, :string
t.column :receivedate, :timestamp
t.column :messageid, :string
t.column :header, :text
t.column :body, :text
t.timestamps
end
enddef self.down
drop_table :emails
end
end
(3) マイグレーションファイルの実行
NetBeansで[データベースマイグレーション]→[現在のバージョンへ]を選択します。
(in D:/Rails_Projects/Appli010)
== CreateEmails: migrating ===================================================
-- create_table(:emails)
-> 0.1560s
== CreateEmails: migrated (0.1560s) ==========================================
1-4.テーブルattachmentの作成
(1) モデルの作成
NetBeansで[生成]を選択
ジェネレータ(G):model
引数(A):Attachment
exists app/models/
exists test/unit/
exists test/fixtures/
create app/models/attachment.rb
create test/unit/attachment_test.rb
create test/fixtures/attachments.yml
exists db/migrate
create db/migrate/20100210001457_create_attachments.rb
(2) マイグレーションファイルの修正
class CreateAttachments < ActiveRecord::Migration
def self.up
create_table :attachments do |t|
t.column :page_id, :integer
t.column :file, :binary
t.column :filename, :string
t.column :description, :string
t.timestamps
end
enddef self.down
drop_table :attachments
end
end
(3) マイグレーションファイルの実行
NetBeansで[データベースマイグレーション]→[現在のバージョンへ]を選択します。
(in D:/Rails_Projects/Appli010)
== CreateAttachments: migrating ==============================================
-- create_table(:attachments)
-> 0.1100s
== CreateAttachments: migrated (0.1100s) =====================================
1-5.リレーションの宣言
class Page < ActiveRecord::Base
has_many :emails
has_many :attachments
end
1-6.メール受信専用モデルの作成
(1) モデルの生成
NetBeansで[生成..]を選択します。
ジェネレータ(G):mailer
引数(A):Mailreceiver
exists app/models/
create app/views/mailreceiver
exists test/unit/
create test/fixtures/mailreceiver
create app/models/mailreceiver.rb
create test/unit/mailreceiver_test.rb
(2) モデルの編集
require 'net/pop'
class Mailreceiver < ActionMailer::Base
@address = 'POP3saver' # <= 自分のPOP3サーバー
@port = 110 # <= ポート番号 110など
@id = 'userid' # <= ユーザーID
@pass = 'password' # <= パスワードdef receive(email)
page = Page.find_by_address(email.from.first) ||
Page.create(:address => email.from.first)
str = email.subject.kconv(Kconv::UTF8, Kconv::JIS) # JIS から UTF8 に変換
page.emails.create(
:subject => str,
:body => email.body,
:header => email.header,
:messageid => email.message_id,
:receivedate => email.date
)if email.has_attachments?
for attachment in email.attachments
str = attachment.original_filename.kconv(Kconv::UTF8, Kconv::JIS)
page.attachments.create({
:file => attachment,
:description => email.subject,
:filename => str
})
end
end
enddef Mailreceiver.r_m
pop = Net::POP3.new(@address, @port)
pop.start(@id, @pass)
if !pop.mails.empty? then
pop.each_mail do |m|
receive(m.pop) # 受信したメールを、「処理」する(DBへ登録)
m.delete # 受信したメールをサーバから削除
end
end
pop.finish
end
end
1-7.動作確認
D:\Rails_Projects\Appli010>ruby script/runner Mailreceiver.r_m
D:\Rails_Projects\Appli010>
1-8.メール送信サーバの設定
# Settings specified here will take precedence over those in config/environment.rb
# In the development environment your application's code is reloaded on
# every request. This slows down response time but is perfect for development
# since you don't have to restart the webserver when you make code changes.
config.cache_classes = false# Log error messages when you accidentally call methods on nil.
config.whiny_nils = true# Show full error reports and disable caching
config.action_controller.consider_all_requests_local = true
config.action_view.debug_rjs = true
config.action_controller.perform_caching = false# Don't care if the mailer can't send
config.action_mailer.raise_delivery_errors = trueconfig.action_mailer.delivery_method = :smtp
config.action_mailer.smtp_settings = {
:address => 'SMTPsever', # <= 自分のSMTPサーバー
:port => 25, # <= ポート番号 25,587など
:authentication => :login, # <= 認証方法 :plain, :login, :cram_md5など
:user_name => "username", # <= ユーザーID
:password => "password", # <= パスワード
:domain => "domain" # <= ドメイン
}
1-9.メール送信専用モデルの作成
(1) モデルの生成
NetBeansで[生成]を選択します。
ジェネレータ(G):mailer
引数(A):Mailsender
exists app/models/
create app/views/mailsender
exists test/unit/
create test/fixtures/mailsender
create app/models/mailsender.rb
create test/unit/mailsender_test.rb
(2) モデルの修正
class Mailsender < ActionMailer::Base
@@default_charset = 'iso-2022-jp'def okuru(okuru)
str = okuru[:subject].kconv(Kconv::JIS, Kconv::UTF8) # UTF8 から JIS に変換
@subject = str
@recipients = okuru[:to]
@from = okuru[:from]
@sent_on = Time.now
str = okuru[:body].kconv(Kconv::JIS, Kconv::UTF8) # UTF8 から JIS に変換
@body = str
@headers["reply-to"] = okuru[:from]
endend
1-10.コントローラrmailerの作成
(1) コントローラの生成
NetBeansで生成を選択
ジェネレート(G):controller
名前(N):rmailer
ビュー(V):list show new okuru ukeru
exists app/controllers/
exists app/helpers/
create app/views/rmailer
exists test/functional/
create app/controllers/rmailer_controller.rb
create test/functional/rmailer_controller_test.rb
create app/helpers/rmailer_helper.rb
create app/views/rmailer/list.html.erb
create app/views/rmailer/show.html.erb
create app/views/rmailer/new.html.erb
create app/views/rmailer/okuru.html.erb
create app/views/rmailer/ukeru.html.erb
(2) コントローラの編集
class RmailerController < ApplicationController
layout "rmailer"def list
@emails = Email.find(:all)
enddef show
@email = Email.find(params[:id])
enddef new
enddef okuru
@okuru = params[:okuru]
logger.info "EMAIL:" + params[:okuru][:to]
Mailsender.deliver_okuru(@okuru)
enddef ukeru
job = open('|ruby script/runner Mailreceiver.r_m')
endend
1-11.ビューの作成
(1) 送信用メールフォームの作成
<br>
<div class="box"><%= link_to "受信箱", :action => "list" %>
</div>
<br>
<h1>新規送信メール</h1><% form_for(:okuru, :url =>{:action => "okuru"}) do |f| %><%= error_messages_for('okuru') %>
<table width="60%">
<tr><th>subject</th><td><%= f.text_field(:subject, :size => 60 ) %></td></tr>
<tr><th>to</th><td><%= f.text_field(:to, :size => 60 ) %></td></tr>
<tr><th>from</th><td><%= f.text_field(:from, :size => 60 ) %></td></tr>
<tr><th>body</th><td><%= f.text_area(:body, :cols => 50, :rows => 10 ) %></td></tr>
<tr><th></th><td><%= submit_tag("送信") %>
</table><% end %>
(2) 送信完了通知の作成
<br>
<div class="box"><%= link_to "受信箱", :action => "list" %>
</div>
<br>
<P>送信終了しました</p>
(3) 受信完了通知の作成
<br>
<div class="box"><%= link_to "受信箱", :action => "list" %>
</div>
<br>
<P>受信終了しました</p>
(4) 受信箱の作成
<br>
<div class="box"><%= link_to "新規送信", :action => "new" %><%= link_to "受信", :action => "ukeru" %>
</div>
<br>
<h1>受信箱</h1>
<table>
<thead>
<tr>
<th>subject</th>
<th>address</th>
<th>receivedate</th>
<th></th>
</tr>
</thead><tbody><%-
fg = "ON"
@emails.each do |e|
@page = Page.find(e.page_id)
if fg=="ON" then
fg = "off"
-%>
<tr><%-
else
fg = "ON"
-%>
<tr class="odd"><%- end -%>
<td><%=h e.subject %></td>
<td><%=h @page.address %></d>
<td><%=h e.receivedate %></td>
<td><%= link_to "show", :action => "show", :id => e.id %></td>
</tr><% end %>
</tbody>
</table>
(5) 受信メール表示の作成
<br>
<div class="box"><%= link_to "受信箱", :action => "list" %>
</div>
<br>
<h1>受信メール</h1><% @page = Page.find(@email.page_id) %>
<table width="60%">
<tr><th>subject</th><td><%=h @email.subject %></td></tr>
<tr><th>address</th><td><%=h @page.address %></td></tr>
<tr><th>receivedate</th><td><%=h @email.receivedate %></td></tr>
<tr><th>body</th><td><%=h @email.body %></td></tr>
</table>
1-12.スタイルシートの作成
(1) CSSで使用する画像の準備
/public/images/に透過のtable-back.gifを用意します。
これは見出し部分を立体的に見せる工夫で背景色より薄めの色で枠線を作ります。
(2) IE対応
IE6.0ではtr:hoverが動作しません。
http://www.xs4all.nl/~peterned/csshover.htmlからcsshover.htcをダウンロードし、
ダウンロードしたファイルをcsshover3.htcとリネームして/public/stylesheets/に保存します。
(3) CSSファイルの作成
/* 見出しを作る */
h1 {
padding: 10px;
border: medium solid #5C443A;
color: #5C443A;
font-family: sans-serif;
}
/* 文字に背景色を付ける */
.box a {
text-decoration: none; /* 下線を消す */
background-color: #cdcdcd; /* 背景色を薄い灰色 */
color: #000000; /* 文字を黒色 */
padding: 4px 10px 2px 10px;
}
.box a:link { /* 未訪問のリンク */
background-color: #cdcdcd; /* 背景色を薄い灰色 */
color: #000000; /* 文字を黒色 */
}
.box a:visited { /* 訪問済みのリンク */
background-color: #cdcdcd; /* 背景色を薄い灰色 */
color: #000000; /* 文字を黒色 */
}
.box a:hover { /* マウスがのっているとき */
background-color: #808080; /* 背景色を濃い灰色 */
color: #ffffff; /* 文字を白色 */
}
.box a:active { /* クリック時のリンク */
background-color: #808080; /* 背景色を濃い灰色 */
color: #ffff00; /* 文字を黄色 */
}/* テーブル行に背景色を付ける */
body {
behavior: url(/stylesheets/csshover3.htc);
}table {
border-top:1px solid #5C443A;
border-left:1px solid #5C443A;
border-collapse:collapse;
background:#ffffff;
font-size:90%;
}
caption {
color:#5C443A;
font-weight:bold;
text-align:center;
text-transform: uppercase;
}
thead th, tfoot th, tfoot td {
border-right:1px solid #5C443A;
border-bottom:1px solid #5C443A;
background:#5C443A;
color:#ffffff;
background-image:url(/images/table-back.gif);
background-position:left top;
padding:3px 10px 3px 10px;
text-align:center;
}
td, th {
padding:4px;
}
tbody tr th, tbody tr td {
border-right:1px solid #5C443A;
border-bottom:1px solid #5C443A;
}
tbody tr:hover td, tbody tr:hover th {
background: #996633;
color: #ffffff;
}
tbody tr:hover td a, tbody tr:hover th a {
background: #996633;
color: #ffffff;
}
tbody td a, tbody th a {
border: none;
background: transparent;
color: #000000;
text-decoration: none;
}
tbody td a:hover, tbody th a:hover {
background: #996633;
color: #ffffff;
text-decoration: underline;
}
.odd {
background: #ffeebb;
}
1-13.レイアウトファイルの作成
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"><html xmlns="http://www.w3.org/1999/xhtml"
xml:lang="ja" lang="ja">
<head>
<meta http-equiv="Content-Type"
content="text/html; charset=utf-8"/>
<title>Rmailer</title>
<%= stylesheet_link_tag 'rmailer' %>
</head>
<body><%= yield %></body>
</html>
1-14.動作確認
(1) ブラウザよりhttp://127.0.0.1:3000/rmailer/listによる起動