Skip to content

【データベース】メール通知で[[title]]を入れても、実際のメールにタイトルが表示されない #1006

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
akagane99 opened this issue Oct 18, 2021 · 3 comments · Fixed by #1000
Labels
bug バグ・不具合連絡 plugin(database) データベースプラグイン

Comments

@akagane99
Copy link
Contributor

akagane99 commented Oct 18, 2021

概要

・件名通りです。

実行環境

OS: windows10
ブラウザ: 新Edge
Connect-CMS: 2021/10/18 git pull
php version: 7.3.0

再現手順

件名通り

スクリーンショット

メール設定
image

原因

現時点では、DBテーブルのカラムでtitleがないと、件名表示できない作りになっていたため。
https://github.com/opensource-workshop/connect-cms/blob/master/app/Models/Common/BucketsMail.php#L27

        // [[title]]
        $notice_body = str_ireplace('[[title]]', $post->title, $notice_body);

対応案

$post->title, の箇所のカラム名を設定できるようにプログラム修正する。

@akagane99 akagane99 added bug バグ・不具合連絡 plugin(database) データベースプラグイン labels Oct 18, 2021
@akagane99 akagane99 changed the title 【データベース】メール通知で[[title]]を入れても、タイトルが表示されない 【データベース】メール通知で[[title]]を入れても、メールにタイトルが表示されない Oct 18, 2021
@akagane99 akagane99 changed the title 【データベース】メール通知で[[title]]を入れても、メールにタイトルが表示されない 【データベース】メール通知で[[title]]を入れても、実際のメールにタイトルが表示されない Oct 18, 2021
@akagane99
Copy link
Contributor Author

akagane99 commented Oct 19, 2021

概要

  • 2件メールキューで問題が出た。
  • メールキューの問題点
    • メールキューに入っているジョブ PostNoticeJob がコンストラクタで Eloquent モデルを受け入れる場合、PostNoticeJob でuse してる SerializesModelsトレイトの機能で、モデルの識別子だけがキューにシリアル化して、DBの jobs テーブルの おそらくpayload (longtext型、max 4GB)カラムに格納される。
    • ジョブが実際に処理されると、キュー システムはデータベースからモデルインスタンス全体を自動的に再取得する。
      • このため、物理削除したモデルは、再取得時にエラーでこける。(論理削除はデータがあるため、こけない)
    • また、モデルの変数 $post をキューに渡して $post->title $post->id をメールに埋め込んでいるけど、テーブル構造は各プラグインで異なるため、例えば、 $post->title はデータベースでは表示できない問題がある事が今回わかった。
    • また他の項目を埋め込みたい場合に汎用性がない。

対応案

メールキューのモデルの変数 $post をやめて 単なる配列の $data で titleや id その他埋め込みタグをまかなう。
⇒ これで対応する。

(詳細)メールキュー送信の流れ

データベースの投稿通知を例に説明。

・データベースで記事を登録時にメール送信処理が呼ばれる
 DatabasesPlugin::publicStore()
  $this->sendPostNotice($databases_inputs, $before_databases_inputs, 'detail');

・親クラス UserPluginBase:: sendPostNotice() 呼ばれ、(キュー登録 ※1)と(キュー実行 ※2)が行われる。
 UserPluginBase:: sendPostNotice() 内
  // キュー登録
  PostNoticeJob::dispatch($this->frame, $this->buckets, $post_row, $title, $show_method, "notice_create");
   // 非同期でキューワーカ実行
  $this->asyncQueueWork();

(※1 キュー登録)
// dispatchメソッドへ渡す引数は、ジョブのコンストラクタへ渡されます。
App\Jobs\PostNoticeJob::__construct()
・コンストラクタで、プライベートクラス変数に値をセットしています。
・この時、ジョブクラスは SerializesModelsトレイトを使っていて、ジョブ(キュー)は、DBの jobs テーブルに一度格納されます。
 ・キューに入っているジョブがコンストラクタで Eloquent モデルを受け入れる場合、モデルの識別子だけがキューにシリアル化されます。

(※2 キュー実行)
 ・ジョブが実際に処理されると、キュー システムはデータベースからモデルインスタンス全体を自動的に再取得します。

・キューを実行して、Mail::to()でメール送信する。メールの内容はnew PostNotice()から取得。
 PostNoticeJob::handle() 内
  Mail::to($notice_address)->send(new PostNotice($this->frame, $this->bucket, $this->post, $this->title, $this->show_method, $this->notice_method, $bucket_mail));

App\Mail\PostNotice::__construct() で値をセット
App\Mail\PostNotice::build() でメール内容をセット。定型文は 'mail.post.post_text‘。

    public function build()
    {
        return $this->text('mail.post.post_text')
                    ->subject($this->bucket_mail->notice_subject)
                    ->with([
                        'frame'         => $this->frame,
                        'bucket'        => $this->bucket,
                        'post'          => $this->post,
                        'title'         => $this->title,
                        'show_method'   => $this->show_method,
                        'notice_method' => $this->notice_method,
                        'bucket_mail'   => $this->bucket_mail,
                    ]);
    }


定型文 'mail.post.post_text‘。
resources\views\mail\post\post_text.blade.php

{{$bucket_mail->getFormatedNoticeBody($frame, $bucket, $post, $title, $show_method, $notice_method)}}


BucketsMail::getFormatedNoticeBody() 参照
ここで埋め込みタグを使ってる。
問題の モデル変数 $post は、他のメソッドも含めて今のところ $post->title $post->id 位しか使っていない。

namespace App\Models\Common;

(省略)

class BucketsMail extends Model
{

(省略)

    public function getFormatedNoticeBody($frame, $bucket, $post, $title, $show_method, $notice_method, $delete_comment = null)
    {
        $notice_body = $this->notice_body;

        // [[method]]
        $notice_body = str_ireplace('[[method]]', NoticeJobType::getDescription($notice_method), $notice_body);

        // [[title]]
        // $notice_body = str_ireplace('[[title]]', $post->title, $notice_body);
        $notice_body = str_ireplace('[[title]]', $title, $notice_body);

        // [[url]]
        $url = url('/') . '/plugin/' . $bucket->plugin_name . '/' . $show_method . '/' . $frame->page_id . '/' . $frame->id . '/' . $post->id . '#frame-' . $frame->id;
        $notice_body = str_ireplace('[[url]]', $url, $notice_body);

        // [[delete_comment]]
        $notice_body = str_ireplace('[[delete_comment]]', $delete_comment, $notice_body);

        return $notice_body;
    }

参考

ジョブのディスパッチ- キュー 6.x Laravel

dispatchメソッドへ渡す引数は、ジョブのコンストラクタへ渡されます。

php - Laravelキューシリアライズモデル特性が関連する値を削除 - スタックオーバーフロー

キューに入っているジョブがコンストラクタで Eloquent モデルを受け入れる場合、モデルの識別子だけがキューにシリアル化されます。ジョブが実際に処理されると、キュー システムはデータベースからモデルインスタンス全体を自動的に再取得します。

@akagane99
Copy link
Contributor Author

akagane99 added a commit that referenced this issue Oct 20, 2021
bugfix: 【データベース】メール通知で[[title]]を入れても、実際のメールにタイトルが表示されないバグ修正 #1006
change: 【データベース】削除のメール通知の同期送信を非同期送信に戻す #1008
bugfix: 【掲示板】関連通知メールが飛ばないバグ修正 #1010
akagane99 added a commit that referenced this issue Oct 20, 2021
bugfix: 【データベース】メール通知で[[title]]を入れても、実際のメールにタイトルが表示されないバグ修正 #1006
change: 【データベース】削除のメール通知の同期送信を非同期送信に戻す #1008
bugfix: 【掲示板】関連通知メールが飛ばないバグ修正 #1010
@akagane99
Copy link
Contributor Author

対応しました。

修正プログラム

49c7c9b

@akagane99 akagane99 linked a pull request Oct 20, 2021 that will close this issue
2 tasks
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug バグ・不具合連絡 plugin(database) データベースプラグイン
Projects
None yet
Development

Successfully merging a pull request may close this issue.

1 participant