それマグで!

知識はカップより、マグでゆっくり頂きます。 takuya_1stのブログ

習慣に早くから配慮した者は、 おそらく人生の実りも大きい。

Ruby でGmailのタグのメールを読み出して保存する。

Gmailでいっぱい添付ファイルが届きました。だけど、一個一個保存するのがとっても面倒くさいので、Rubyで処理することにしました。通常であればIMAPで落とすんだろうけど、ファイル名や差出人で保存先を分けたかったので、IMAP断念してRubyでやりました。

rubyGmailを取り出す際のポイント

rubygems の gmai を使うと楽
ラベルのアクセスには シンボルを使う。
パスワードにはPitを使うと楽

Gmailへのアクセス

require 'rubygems'
require 'pit'
require 'gmail'

data = Pit.get('takuyaXXX@gmail.com')
gmail = Gmail.new(:plain,data["username"], data["password"]);

ラベル内のメールを取り出す。

gmail.label("Inbox".to_sym ).all.each{|l| puts l}

ここでのポイントは、文字列をシンボルに変える.to_sym をつかう。日本語のto_symはあれれ・・動かなかった。(´Д⊂グスン

メールの取り出し

取り出したメールは Messageクラスになっている。

l = gmail.label("Inbox".to_sym ).all.first
m = l.message #=> メールクラス

このクラスの扱い方は https://github.com/mikel/mail/ を参照する。

メールの中身へのアクセス

メールの各パーツへのアクセスは次の通り

l = gmail.label("Inbox".to_sym ).all.first
m = l.message # メールクラス
m.subject.toutf8  #題名
m.header["from"].value  #送信元アドレス。
m.date.strftime("%Y-%m-%d") #送信日
body = m.body   # メール本文
m.parts.select{|e| e.attachment?}#添付ファイル

各パーツを表示する際の変数の変換

上記の方法で取り出せる。もう少し詳細に書いておきます。

メールの本文
body = m.body.decoded.utf8
題名(タイトル)
subject = m.subject.toutf8
送信者
m.header["from"].value  #送信元アドレス。
送信日付
m.date.strftime("%Y-%m-%d") #送信日
添付ファイル
m.parts.select{|e| e.attachment?}

添付ファイルの中身

m.parts.select{|e| e.attachment?}.map{|e| 
  puts e
  {:name=> e.filename.toutf8, :content => e.decoded }
 }

まとめたらこんな感じ。

デスクトップに送信日毎のディレクトリつくって、その中に、送信者単位のフォルダを作る

#!/usr/bin/env rubyrequire 'openssl'
OpenSSL::SSL::VERIFY_PEER = OpenSSL::SSL::VERIFY_NONE
require 'pp'
require 'rubygems'
require 'pit'
require 'gmail'
require 'kconv'
require 'mechanize'
require 'nokogiri'

data = Pit.get('takuyaXXX@gmail.com')
gmail = Gmail.new(:plain,data["username"], data["password"]);
tag = "提出レポート"

gmail.label(tag.to_sym ).all.each{|l|
     m = l.message
     body = m.body
     dirname="~/Desktop/repo/"+m.date.strftime("%Y-%m-%d")+"/"+m.header["from"].value.toutf8
     dirname = File.expand_path dirname
     FileUtils.mkdir_p( dirname )
     Dir.chdir(dirname) {
          m.parts.select{|e| e.attachment?}.each{|e|
               begin
               name =  e.filename
               name = name.toutf8
               f = open(name,"w"){|f|
                    body = e.body.decoded
                    body = body.toutf8 if (e.content_type =~ %r"^text")
                    f.puts body
               }
               rescue => e
                    puts "-"*20
                    puts "エラー#{dirname} の attachment処理"
                    puts e
               end
          }
          open("title.txt","w"){|f|
               begin
               f.puts m.subject.toutf8
               rescue => e
                    puts "-"*20
                    puts "エラー#{dirname} の Subject部処理"
                    puts e
               end
          }
          open("index.txt","w") {|f|
               begin
               f.puts m.text_part.body.decoded.toutf8
               rescue => e
                    puts "-"*20
                    puts "エラー#{dirname} の Text部処理"
                    puts e
               end

          }
     }
}