9
6

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

【Flutter】Flutterアプリからメールを送信するパッケージについて

Posted at

まえがき

2020年からFlutterの勉強を初めました。
Firebase連携でアプリを作っているのですが、その時ユーザー作成したタイミングとかで認証メールってどうやって送るんだろと思いました。

結果それはFirebase Authenticationの機能であるので、コード一文だけでできるのですが、
調べる中で、メール関係のパッケージってたくさんあるんだなと知りました。

メールを送信するんだろうなと思われるパッケージでもいくつかあって、何が違うのかよくわからないんですよね。

なのでよく見るこの二つを使ってみました。

とはいえ、深いところはあまりわからず、表面的な使い方を紹介すると言う記事になっているので、そこらへんはご了承を。

Firebaseから認証メールの送り方も最後に簡単に説明しますね、

url_launcher

このパッケージは僕は前にも記事を書いたのですが。→url_launcherの使い方
URLをアプリ内で起動させるパッケージです。

その中の機能はURLを起動させるだけでなく、メール送信や電話やSMSなどがあります。

今回はそのメール送信についてですね

flutter_email_sender

このパッケージは単純にメールを送るためのパッケージですね

こっちの方が他の機能がない分シンプルでいいかも

サンプル

フォームにメールアドレスを入力してそこのメールアドレスにメールを送るというサンプルを作成しました。

送り元のメールアドレスは、デバイスのメールアドレスが使用されるので実機でテストしてみてください。
(ちなみに僕はiOSです。)

import 'package:flutter/material.dart';
import 'package:url_launcher/url_launcher.dart';
import 'package:flutter_email_sender/flutter_email_sender.dart';

class MailPackage extends StatefulWidget {
  @override
  State<StatefulWidget> createState() => _MailPackage();
}

class _MailPackage extends State<MailPackage> {
  TextEditingController emailController = TextEditingController();

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('メールパッケージ'),
      ),
      body: Container(
        padding: EdgeInsets.all(30),
        child: Column(
          mainAxisAlignment: MainAxisAlignment.center,
          children: [
            TextFormField(
              controller: emailController,
              decoration: InputDecoration(hintText: 'メールアドレスを入力してください'),
            ),
            RaisedButton(
              child: Text('url_launcherで送る'),
              onPressed: () {
                urlLauncherMail();
              },
            ),
            RaisedButton(
              child: Text('flutter_email_senderで送る'),
              onPressed: () {
                flutterEmailSenderMail();
              },
            )
          ],
        ),
      ),
    );
  }

//url_launcherを使ってメールを送信
  urlLauncherMail() {
    final Uri _emailLaunchUri = Uri(
      scheme: 'mailto',
      path: '${emailController.text}',
      queryParameters: {
        'subject': 'url_launcherを使ってメールを送ります!',
        'body': '${Template().text}'
      },
    );

    return launch(
      _emailLaunchUri.toString(),
    );
  }

//flutter_email_senderを使ってメールを送信
  flutterEmailSenderMail() async {
    final Email email = Email(
      body: '${Template().text}',
      subject: 'flutter_email_senderを使ってメールを送っています!',
      recipients: ['${emailController.text}'],
      attachmentPaths: ['images/sample1.png'],
    );

    await FlutterEmailSender.send(email);
  }
}

//本文のテンプレート的な
class Template {
  String text =
      'お疲れ様です。テスト通知です。\n\nメールは届いているでしょうか?\n\n届いておりましたら、お返事お待ちしております。\nこちらのURLもみてくださいね\n\nhttps://qiita.com/ryota47/items/fb8e32f1a409026ba065';
}

import 'package:flutter/material.dart';
import 'package:url_launcher/url_launcher.dart';
import 'package:flutter_email_sender/flutter_email_sender.dart';

class MailPackage extends StatefulWidget {
  @override
  State<StatefulWidget> createState() => _MailPackage();
}

class _MailPackage extends State<MailPackage> {
  TextEditingController emailController = TextEditingController();

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('メールパッケージ'),
      ),
      body: Container(
        padding: EdgeInsets.all(30),
        child: Column(
          mainAxisAlignment: MainAxisAlignment.center,
          children: [
            TextFormField(
              controller: emailController,
              decoration: InputDecoration(hintText: 'メールアドレスを入力してください'),
            ),
            RaisedButton(
              child: Text('url_launcherで送る'),
              onPressed: () {
                urlLauncherMail();
              },
            ),
            RaisedButton(
              child: Text('flutter_email_senderで送る'),
              onPressed: () {
                flutterEmailSenderMail();
              },
            )
          ],
        ),
      ),
    );
  }

//url_launcherを使ってメールを送信
  urlLauncherMail() {
    final Uri _emailLaunchUri = Uri(
      scheme: 'mailto',
      path: '${emailController.text}',
      queryParameters: {
        'subject': 'url_launcherを使ってメールを送ります!',
        'body': '${Template().text}'
      },
    );

    return launch(
      _emailLaunchUri.toString(),
    );
  }

//flutter_email_senderを使ってメールを送信
  flutterEmailSenderMail() async {
    final Email email = Email(
      body: '${Template().text}',
      subject: 'flutter_email_senderを使ってメールを送っています!',
      recipients: ['${emailController.text}'],
      attachmentPaths: ['images/sample1.png'],
    );

    await FlutterEmailSender.send(email);
  }
}

//本文のテンプレート的な
class Template {
  String text =
      'お疲れ様です。テスト通知です。\n\nメールは届いているでしょうか?\n\n届いておりましたら、お返事お待ちしております。\nこちらのURLもみてくださいね\n\nhttps://qiita.com/ryota47/items/fb8e32f1a409026ba065';
}

説明

全体は、フォームとボタン二つを配置して、各パッケージのメール送信ができるように関数を作りボタンの中に置きました。
メールの本文用のテンプレートとなるTemplateクラスも作ってみました。

url_launcherの使い方

url_launcherパッケージを使ってメールを送信するのはこちらのコードです。

urlLauncherMail() {
  final Uri _emailLaunchUri = Uri(
    scheme: 'mailto',
    path: '${emailController.text}',
    queryParameters: {
      'subject': 'url_launcherを使ってメールを送ります!',
      'body': '${Template().text}'
    },
  );

  return launch(
    _emailLaunchUri.toString(),
  );
}

Uriクラスを定義して、

  • schememailto
  • path:送る先のメールアドレス
  • queryParameters:内容。subjectが件名、bodyが本文

それを、launchの引数で渡すことで、メール送信画面に遷移します。toString()することを忘れずに。

flutter_email_senderの使い方

flutter_email_senderを使ってメールを送信するのはこちらのコードです。

flutterEmailSenderMail() async {
  final Email email = Email(
    body: '${Template().text}',
    subject: 'flutter_email_senderを使ってメールを送っています!',
    recipients: ['${emailController.text}'],
  );

  await FlutterEmailSender.send(email);
}

Email

  • body:本文
  • subject:件名
  • recipients:送る先のメールアドレス
    他にもcc,bcc,isHTML,attachmentPathsを渡せます。
    attachmentPathsはなんなのかはまだちょっと理解できてないです。。

これをFlutterEmailSender.send(email)のように引数で渡せばメール送信画面に遷移します。
またrecipients,cc,bccList<String>で定義されているため、複数のメールアドレスを渡すことができそうです。

違いと、どっちがいいか

二つともコードはなんとなく似ていますが、この二つのパッケージは大きな違いがあります。

それぞれメール送信画面に遷移するんですが、
url_launcherはメールのアプリに遷移します。(おそらくユニバーサルリンクを踏んでいる)したがって、メールを送信した後はメールのアプリを開いている状態になります。

しかしflutter_email_senderはそのアプリ内でメール送信画面が起動します。したがってメールを送信してもそのアプリが開かれた状態になります。

これならflutter_email_senderの方を使っちゃいそうだな〜

flutter_email_senderの方が本文、件名を設定するのも若干簡単だし。
cc,bccが簡単に作れるので便利そう。

ソースコードを読んでみた感想

flutter_email_senderのEmailクラスを開いたら、すごくシンプルで、「あれもしかしてメール送信ってパッケージ使わなくても簡単なのか?」と思いました。
しかしreturnで返してるMethodChannelを開くとなんか複雑で、ヒョエ〜ってなってやめました。

Firebaseからメール送る方法

最後におまけでFirebase Authenticationからメールを送る方法を紹介します。
Firebase Authenticationをブラウザで開き、Templatesを開きます。
そこに、メール認証のテンプレートがあります。

  • メールアドレスの確認
FirebaseUser currentUser = await FirebaseAuth.instance.currentUser();

await currentUser.sendEmailVerification();
  • パスワードの再設定
FirebaseAuth auth = FirebaseAuth.instance;

await auth.sendPasswordResetEmail(email: null);
  • メールアドレスの変更
FirebaseAuth auth = FirebaseAuth.instance;

await auth.sendSignInWithEmailLink(
    email: null,
    url: null,
    handleCodeInApp: null,
    iOSBundleID: null,
    androidPackageName: null,
    androidInstallIfNotAvailable: null,
    androidMinimumVersion: null);

これで送れそうです。
nullのところにはそれぞれ値を入れる必要があります。
メールアドレスの変更には、リセット用のリンクがありその時は匿名のサインインが必要になるらしく
匿名のサインイン機能をオンにしておく必要がありそうです。
(まだちゃんと試してないので、違かったらすいません。)

9
6
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
9
6

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?