SHOEISHA iD

※旧SEメンバーシップ会員の方は、同じ登録情報(メールアドレス&パスワード)でログインいただけます

CodeZine編集部では、現場で活躍するデベロッパーをスターにするためのカンファレンス「Developers Summit」や、エンジニアの生きざまをブーストするためのイベント「Developers Boost」など、さまざまなカンファレンスを企画・運営しています。

Perlで作るモバイルサイトのコツ

Perlで作るモバイルサイトのコツ:第7回

絵文字を含んだメールを送信する


  • このエントリーをはてなブックマークに追加

サンプルプログラム

 サンプルプログラムで、絵文字を含むメールを送信してみましょう。前述の規則にのっとり、ドコモとEZwebにはSjift_JISで、SoftBankにはUTF-8で送信します。

 また、<emoji:番号> という独自の絵文字用の番号を作り、それぞれのキャリアごとにどの絵文字コードを使うかをマップさせています。

 絵文字コードについては各キャリアのサポートページを参照ください。

 それでは、サンプルプログラムを見ていきましょう。

send_mail.pl

 メール送信スクリプトです。後述のEmojiMailモジュールを使用してメールを送信します。

send_mail.pl(UTF-8で記述)
#!/usr/local/bin/perl

use strict;
use warnings;
use EmojiMail;

my $mail = EmojiMail->new({
    from    => 送信元アドレス,
    to      => 送信先アドレス,
    subject => 'こんにちは<emoji:1>',
    body    => '天気がいいから、テニスしようよ<emoji:2>',
    emoji_map => 後述の絵文字マップファイルのパス,
});

$mail->send;

emoji_map.yaml

 絵文字マップファイルです。YAML形式で記述しています。例えば、ドコモの端末に送信するメール本文に<emoji:1>と記述した場合、<emoji:1>の部分が太陽の絵文字(F89F)に置換されることになります。

emoji_map.yaml
I:          # ドコモ
  1: F89F   # 太陽の絵文字のS-JISコード16進数値
  2: F8B6   # テニスの絵文字のS-JISコード16進数値

E:          # EZweb
  1: F660   # 太陽の絵文字のKDDI絵文字用Shift_JISコード値
  2: F690   # テニスの絵文字のKDDI絵文字用Shift_JISコード値

S:          # SoftBank
  1: E04A   # 太陽の絵文字のunicode値
  2: E015   # テニスの絵文字のunicode値

EmojiMail.pm

 メール送信部分の本体です。キャリアごとに絵文字を含んだメールを生成します。送信先メールアドレスによるキャリアの判別はMail::Address::MobileJpモジュールを使って行っています。文字コードの変換にはEncodeを使用しています。

EmojiMail.pm(UTF-8で記述)
package EmojiMail;

use strict;
use warnings;
use MIME::Lite;
use MIME::Base64 ();
use Mail::Address::MobileJp;
use Encode;
use Unicode::Transform ();
use YAML::Syck;

sub new {
    my ($class, $opt) = @_;
    my $self = bless {
        from    => $opt->{from},
        to      => $opt->{to},
        subject => $opt->{subject},
        body    => $opt->{body},
    }, $class;
    $self->{emoji_map} = YAML::Syck::LoadFile($opt->{emoji_map});
    $self->build;
    return $self;
}

sub build {
    my $self = shift;
    my $message = MIME::Lite->new(
        From     => $self->{from},
        To       => $self->{to},
        Subject  => $self->subject,
        Data     => $self->body,
        Encoding => 'base64',
    );
    $message->attr('content-type.charset' => $self->charset);
    $message->attr("Content-disposition"  => "");
    $message->field_order(
        'MIME-Version', 'Content-Type', 'Content-Transfer-Encoding');
    $self->{message} = $message;
}

sub send { shift->{message}->send }

sub subject {
    my $self = shift;
    my $subject = $self->converter->($self->{subject});
    return '=?SHIFT-JIS?B?'. MIME::Base64::encode($subject)
                           .'?=' if is_imode($self->{to});
    # EZwebではMIMEエンコードをすると化けるのでそのまま送信する
    return $subject if is_ezweb($self->{to});
    return '=?UTF-8?B?'. MIME::Base64::encode($subject)
                       .'?=' if is_softbank($self->{to});
}

sub body {
    my $self = shift;
    my $body = $self->converter->($self->{body});
    return $body;
}

sub converter {
    my $self = shift;
    return sub {
        my $content = $self->encode_content->(shift);
        $content =~ s{(<emoji:(\d)>)}{
            my $code = $self->emoji_map->{$2};
            if (defined $code) {
                $self->code_to_emoji($code);
            }
        }eg;
        return $content;
    }
}

sub encode_content {
    my $self = shift;
    return sub {
        my $content = shift;
        return encode('Shift_JIS', decode('utf-8', $content))
            if is_imode($self->{to});
        return encode('Shift_JIS', decode('utf-8', $content))
            if is_ezweb($self->{to});
        return $content if is_softbank($self->{to});
    }
}

sub emoji_map {
    my $self = shift;
    return $self->{emoji_map}->{I} if is_imode($self->{to});
    return $self->{emoji_map}->{E} if is_ezweb($self->{to});
    return $self->{emoji_map}->{S} if is_softbank($self->{to});
}

sub code_to_emoji {
    my ($self, $code) = @_;
    return pack("H4", $code) if is_imode($self->{to});
    return pack("H4", $code) if is_ezweb($self->{to});
    return Unicode::Transform::unicode_to_utf8(chr(hex($code)))
        if is_softbank($self->{to});
}

sub charset {
    my $self = shift;
    return 'Shift_JIS' if is_imode($self->{to});
    return 'Shift_JIS' if is_ezweb($self->{to});
    return 'UTF-8'     if is_softbank($self->{to});
}

1;

 上記のサンプルを実行すると、下記のようなメールが送信されるはずです。

送信されるメール
件名: こんにちは[太陽の絵文字]
本文: 天気がいいから、テニスしようよ[テニスの絵文字]

まとめ

 今回は、キャリアごとのメール仕様の違いと送信方法を見てきましたが、いかがだったでしょうか。

 今回の方法で重要になってくるのが、端末タイプです。同じキャリアでも端末タイプによって送信方法が異なる上に、送信先のメールアドレスからはその端末タイプを判断することができないので、サイトでメールアドレスと一緒にUserAgentを保存しておいて、それをもとに送信するなどの工夫が必要となるでしょう。

 サイトで絵文字を使う場合と比較すると注意する点が多いかもしれませんが、本稿が参考になれば幸いです。

この記事は参考になりましたか?

  • このエントリーをはてなブックマークに追加
Perlで作るモバイルサイトのコツ連載記事一覧

もっと読む

この記事の著者

村上 洋一郎(ムラカミ ヨウイチロウ)

株式会社ライブドア メディア事業部 モバイルメディア部所属。占いサイトやコミュニティサイトなど、様々なエンタメ系サイトの開発を担当しています。

※プロフィールは、執筆時点、または直近の記事の寄稿時点での内容です

この記事は参考になりましたか?

この記事をシェア

  • このエントリーをはてなブックマークに追加
CodeZine(コードジン)
https://codezine.jp/article/detail/1262 2008/08/26 13:42

おすすめ

アクセスランキング

アクセスランキング

イベント

CodeZine編集部では、現場で活躍するデベロッパーをスターにするためのカンファレンス「Developers Summit」や、エンジニアの生きざまをブーストするためのイベント「Developers Boost」など、さまざまなカンファレンスを企画・運営しています。

新規会員登録無料のご案内

  • ・全ての過去記事が閲覧できます
  • ・会員限定メルマガを受信できます

メールバックナンバー

アクセスランキング

アクセスランキング