Artisan 命令通知所有用户给出 BadMethodCallException

Artisan command notification to all users gives BadMethodCallException

我如何创建一个 artisan 命令来向系统中的所有用户发送数据库通知,其中包含他们在系统中停留多长时间的信息?

我的 SendEmails 命令如下所示:

    <?php

namespace App\Console\Commands;

use Illuminate\Console\Command;
use App\User;
use Illuminate\Support\Facades\Mail;
use App\Mail\UserEmails;
use Illuminate\Support\Facades\Notification;

class SendEmails extends Command
{
    /**
     * The name and signature of the console command.
     *
     * @var string
     */
    protected $signature = 'send:emails';

    /**
     * The console command description.
     *
     * @var string
     */
    protected $description = 'Send Email to allusers';

    /**
     * Create a new command instance.
     *
     * @return void
     */
    public function __construct()
    {
        parent::__construct();
    }

    /**
     * Execute the console command.
     *
     * @return mixed
     */
    public function handle()
    {
        $users = User::all();
        foreach($users as $user){
            $created_at = $user->created_at;
            Notification::send($user, new SendEmailsNotification($created_at));
        }
    }
}

然后我创建了通知 table,迁移了,代码如下:

<?php

namespace App\Notifications;

use Illuminate\Bus\Queueable;
use Illuminate\Notifications\Notification;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Notifications\Messages\MailMessage;

class SendEmailsNotification extends Notification
{
    use Queueable;

    public $created_at;

    public function __construct($created_at)
    {
        $this->created_at = $created_at;
    }

    public function via($notifiable)
    {
        return ['database'];
    }

    public function toMail($notifiable)
    {
        return (new MailMessage)
                    ->line('The introduction to the notification.')
                    ->action('Notification Action', url('/'))
                    ->line('Thank you for using our application!');
    }

    public function toArray($notifiable)
    {
        return [
        ];
    }
}

User.php:

<?php

namespace App;

use Illuminate\Notifications\Notifiable;
//use Illuminate\Contracts\Auth\MustVerifyEmail;
use Illuminate\Foundation\Auth\User as Authenticatable;

class User extends Authenticatable
{
    //use Notifiable;

    /**
     * The attributes that are mass assignable.
     *
     * @var array
     */
    protected $fillable = [
        'name', 'email', 'password', 'address', 'image'
    ];

    /**
     * The attributes that should be hidden for arrays.
     *
     * @var array
     */
    protected $hidden = [
        'password', 'remember_token',
    ];

    /**
     * The attributes that should be cast to native types.
     *
     * @var array
     */
    protected $casts = [
        //'email_verified_at' => 'datetime',
        'address' => 'array'
    ];

    protected $uploads = '/images/';

    public function getImageAttribute($image){
        return $this->uploads . $image;
    }

    public function contacts(){
        return $this->hasMany('App\Contact');
    }
}

当我 运行 artisan 命令 "php artisan send:emails" 我在控制台中看到以下错误:

BadMethodCallException : Call to undefined method App\User::routeNotificationFor()

如何向所有用户发送通知?

首先,您需要按照其他答案中的建议取消注释 use Notifiable;。现在 Notification::send() 用于向多个用户发送通知,它希望第一个参数是可通知对象(即用户)的集合,而不是对象。要在循环中单独发送通知,您应该这样做:

foreach($users as $user) {
    $created_at = $user->created_at;
    $user->notify(new SendEmailsNotification($created_at));
}

但是由于您的通知中已经包含可通知对象,因此更好的解决方案是这样的:

您的通知class:

use Queueable;

public $created_at;

public function __construct()
{
    
}

public function via($notifiable)
{
    return ['database'];
}

public function toMail($notifiable)
{
    $created_at = $notifiable->created_at;
    return (new MailMessage)
                ->line('The introduction to the notification.')
                ->action('Notification Action', url('/'))
                ->line('Thank you for using our application!');
}

public function toArray($notifiable)
{
    $created_at = $notifiable->created_at;
    return [
    ];
}

并且在您的 Artisan 命令中:

$users = User::all();
Notification::send($users, new SendEmailsNotification());

您只需取消注释 // use Notifiable 行。

Notifiable 特征包括另外两个特征,其中之一是 RoutesNotifications 特征。

RoutesNotifications 特征是您需要能够将通知发送到 User


此外,您应该能够将 SendEmails 命令中的代码简化为:

Notification::send(User::all(), new SendEmailsNotification()); 

而不是显式传递 created_at,您可以从 SendEmailsNotification 中的 $notifiable 访问它(因为在这种情况下 $notifiable 将是 User 模型)例如

public function toArray($notifiable)
{
    return [
        'data' => 'Account Created' . $notifiable->created_at->diffForHumans()
    ];
}

}