如何使用事件侦听器向用户显示警报消息
How to show an alert message to a user with Event Listener
我创建了一个名为 UserWalletNewTransaction.php
的事件并将其添加到其中:
public $transaction;
public function __construct($transaction) {
$this->$transaction = $transaction;
}
现在为了在控制器上触发这个事件,我编码如下:
$newTransaction = UserWalletTransaction::create(['user_id' => $user_id, 'wallet_id' => $wallet_id, 'creator_id' => $creator_id, 'amount' => $amount_add_value, 'description' => $trans_desc]);
event(new UserWalletNewTransaction($newTransaction));
然后在 Listener UserWalletNotification.php
,我尝试了:
public function handle(UserWalletNewTransaction $event) {
$uid = $event->transaction->user_id;
$user = User::find($uid);
// now sends alert message to the user
}
所以情况是,当管理员为自定义用户创建新交易时,必须为 him/her 发送新的警报消息,让 him/her 知道为 [= 添加了新交易27=].
但我真的不知道该怎么做..所以如果你知道,请告诉我,我将不胜感激...
提前致谢。
如果提醒是指在 Web 界面上显示消息,请使用闪存数据。
https://laravel.com/docs/5.8/session#flash-data
$newTransaction = UserWalletTransaction::create(...);
event(new UserWalletNewTransaction($newTransaction));
$request->session()->flash('status', 'Transaction done.');
return view(...)
<span>{{ session('status') }}</span>
如果您的意思是发送电子邮件,只需在您的侦听器中使用 Mail
门面来发送邮件。
https://laravel.com/docs/5.8/mail#sending-mail
public function handle(UserWalletNewTransaction $event) {
$uid = $event->transaction->user_id;
$user = User::find($uid);
Mail::to($user)->send(new TransactionDoneMail($event->transaction)); // TransactionDoneMail being your mailable class, made with "php artisan make:email TransactionDoneMail"
}
文档中有关于如何构建可邮寄的很好的示例 class。
我相信你想做的是异步通知。
好吧,如果您真的是指即时消息 - 那些存储在会话中的消息 - 那就没那么容易了。
正常步骤是为当前登录网站的用户创建 flash 消息,存储在当前用户唯一的会话中。只能为该用户显示。
你想要的是创建一个 flash 消息作为管理员(从管理员的角度),然后只有管理员可以显示它。
我会这样做,在存储这些通知消息时创建新的 table。一些 table 的列如 id, user_id, message, type, created_date, shown_date
。管理员将为每个用户放置 alert/notification 条消息。然后创建 class(例如可以在控制器中),它将为每个用户检查此 table,如果有新的尚未显示的消息,则在当前用户的快速消息中正常显示它。不要忘记如图所示标记该消息。就是这样。
自定义解决方案就这么多。我相信一定有一些例如 jQuery/other Jvascript 插件或 Laravel 用于 异步通知 的插件,请检查那些。
在“提醒”客户方面,您可以做很多不同的事情。
一种方法是在您的事件侦听器中发送电子邮件或短信。请参阅 https://laravel.com/docs/5.8/mail 通过电子邮件获得帮助。
另一种方法是使用浏览器推送通知。您可以为此使用 OneSignal。您可以将前端设置为向客户用户显示警报,询问他们是否愿意订阅推送通知。当他们订阅时,您将取回该特定用户的 ID。对您的 Laravel 应用程序进行 API 调用,并将该 ID 存储在用户 table 中(您将需要迁移)。然后从您的事件侦听器中,您可以调用 OneSignal 的 API 并向用户发送通知,该通知将在他们的计算机上弹出。
这里是使用 OneSignal 通过 API 向用户发送事件的示例:
您的 OneSignal 服务:
<?php
namespace App\Services;
use App\User;
use GuzzleHttp\Client;
class OneSignalService
{
public function sendNotificationToUser(User $user, string $title, string $message, string $url, string $subtitle = null)
{
if (!$user->one_signal_id) {
return;
}
$fields = [
'app_id' => config('services.onesignal.app_id'),
'include_player_ids' => [$user->one_signal_id],
'headings' => ['en' => $title],
'contents' => ['en' => $message],
'url' => $url,
];
if ($subtitle) {
$fields['subtitle'] = ['en' => $subtitle];
}
$client = new Client([
'base_uri' => 'https://onesignal.com/api/v1/',
'headers' => [
'Content-Type' => 'application/json; charset=utf-8',
'Authorization' => 'Basic <<API_KEY>>',
]
]);
$client->request('POST', 'notifications', [
'json' => $fields
])
}
}
用户钱包通知:
public function handle(UserWalletNewTransaction $event) {
$uid = $event->transaction->user_id;
$user = User::find($uid);
// now sends alert message to the user
$oneSignal = new OneSignalService();
$oneSignal->sendNotificationToUser($user, 'New Transaction', 'You have a new transaction', 'yourwebsite.com');
}
我将通过 broadcasting, which would use websockets to instantly send the customer user an alert to their browser, in which you could then display a popup of some sort. You could install Laravel Echo Server, but to keep things simple you can use Pusher 来解决这个问题。按照指南在您的网站前端安装。
然后,创建一个特定于客户用户“transaction.created.{{USER ID}}”的私人频道,并在您的前端收听它。
在 Laravel 中,您将通过 composer 安装 PHP Pusher SDK。
然后在您的 .env 文件集中:
BROADCAST_DRIVER=pusher
接下来,在 Laravel 的路由目录中打开 channels.php 并添加:
Broadcast::channel('transaction.created.{id}', function ($user, $id) {
return (int) $user->id === (int) $id;
});
这将验证您的用户对私人频道的身份验证。
创建一个 Laravel 事件:
<?php
namespace App\Events;
use App\User;
use Illuminate\Broadcasting\Channel;
use Illuminate\Broadcasting\InteractsWithSockets;
use Illuminate\Broadcasting\PresenceChannel;
use Illuminate\Broadcasting\PrivateChannel;
use Illuminate\Contracts\Broadcasting\ShouldBroadcastNow;
use Illuminate\Foundation\Events\Dispatchable;
use Illuminate\Queue\SerializesModels;
class TransactionCreated implements ShouldBroadcastNow
{
use Dispatchable, InteractsWithSockets, SerializesModels;
public $user = null;
public $transaction = null;
/**
* Create a new event instance.
*
* @return void
*/
public function __construct(User $user, UserWalletTransaction $transaction)
{
$this->user = $user;
$this->transaction = $transaction;
}
public function broadcastWith(): array
{
return $this->transaction->toArray(); //Or whatever information you want to send to the front end
}
public function broadcastAs(): string
{
return 'TransactionCreated';
}
/**
* Get the channels the event should broadcast on.
*
* @return Channel|array
*/
public function broadcastOn()
{
return new PrivateChannel('transaction.created.' . $this->user->id);
}
}
从 UserWalletNotification 触发事件:
public function handle(UserWalletNewTransaction $event) {
$uid = $event->transaction->user_id;
$user = User::find($uid);
// now sends alert message to the user
event(new TransactionCreated($user, $event->transaction));
}
最后,当您的私人频道的回调函数被点击时,创建某种弹出窗口并将其显示在前端。
如果您需要更多帮助,请随时发表评论。
我创建了一个名为 UserWalletNewTransaction.php
的事件并将其添加到其中:
public $transaction;
public function __construct($transaction) {
$this->$transaction = $transaction;
}
现在为了在控制器上触发这个事件,我编码如下:
$newTransaction = UserWalletTransaction::create(['user_id' => $user_id, 'wallet_id' => $wallet_id, 'creator_id' => $creator_id, 'amount' => $amount_add_value, 'description' => $trans_desc]);
event(new UserWalletNewTransaction($newTransaction));
然后在 Listener UserWalletNotification.php
,我尝试了:
public function handle(UserWalletNewTransaction $event) {
$uid = $event->transaction->user_id;
$user = User::find($uid);
// now sends alert message to the user
}
所以情况是,当管理员为自定义用户创建新交易时,必须为 him/her 发送新的警报消息,让 him/her 知道为 [= 添加了新交易27=].
但我真的不知道该怎么做..所以如果你知道,请告诉我,我将不胜感激...
提前致谢。
如果提醒是指在 Web 界面上显示消息,请使用闪存数据。
https://laravel.com/docs/5.8/session#flash-data
$newTransaction = UserWalletTransaction::create(...);
event(new UserWalletNewTransaction($newTransaction));
$request->session()->flash('status', 'Transaction done.');
return view(...)
<span>{{ session('status') }}</span>
如果您的意思是发送电子邮件,只需在您的侦听器中使用 Mail
门面来发送邮件。
https://laravel.com/docs/5.8/mail#sending-mail
public function handle(UserWalletNewTransaction $event) {
$uid = $event->transaction->user_id;
$user = User::find($uid);
Mail::to($user)->send(new TransactionDoneMail($event->transaction)); // TransactionDoneMail being your mailable class, made with "php artisan make:email TransactionDoneMail"
}
文档中有关于如何构建可邮寄的很好的示例 class。
我相信你想做的是异步通知。
好吧,如果您真的是指即时消息 - 那些存储在会话中的消息 - 那就没那么容易了。
正常步骤是为当前登录网站的用户创建 flash 消息,存储在当前用户唯一的会话中。只能为该用户显示。
你想要的是创建一个 flash 消息作为管理员(从管理员的角度),然后只有管理员可以显示它。
我会这样做,在存储这些通知消息时创建新的 table。一些 table 的列如 id, user_id, message, type, created_date, shown_date
。管理员将为每个用户放置 alert/notification 条消息。然后创建 class(例如可以在控制器中),它将为每个用户检查此 table,如果有新的尚未显示的消息,则在当前用户的快速消息中正常显示它。不要忘记如图所示标记该消息。就是这样。
自定义解决方案就这么多。我相信一定有一些例如 jQuery/other Jvascript 插件或 Laravel 用于 异步通知 的插件,请检查那些。
在“提醒”客户方面,您可以做很多不同的事情。
一种方法是在您的事件侦听器中发送电子邮件或短信。请参阅 https://laravel.com/docs/5.8/mail 通过电子邮件获得帮助。
另一种方法是使用浏览器推送通知。您可以为此使用 OneSignal。您可以将前端设置为向客户用户显示警报,询问他们是否愿意订阅推送通知。当他们订阅时,您将取回该特定用户的 ID。对您的 Laravel 应用程序进行 API 调用,并将该 ID 存储在用户 table 中(您将需要迁移)。然后从您的事件侦听器中,您可以调用 OneSignal 的 API 并向用户发送通知,该通知将在他们的计算机上弹出。
这里是使用 OneSignal 通过 API 向用户发送事件的示例:
您的 OneSignal 服务:
<?php
namespace App\Services;
use App\User;
use GuzzleHttp\Client;
class OneSignalService
{
public function sendNotificationToUser(User $user, string $title, string $message, string $url, string $subtitle = null)
{
if (!$user->one_signal_id) {
return;
}
$fields = [
'app_id' => config('services.onesignal.app_id'),
'include_player_ids' => [$user->one_signal_id],
'headings' => ['en' => $title],
'contents' => ['en' => $message],
'url' => $url,
];
if ($subtitle) {
$fields['subtitle'] = ['en' => $subtitle];
}
$client = new Client([
'base_uri' => 'https://onesignal.com/api/v1/',
'headers' => [
'Content-Type' => 'application/json; charset=utf-8',
'Authorization' => 'Basic <<API_KEY>>',
]
]);
$client->request('POST', 'notifications', [
'json' => $fields
])
}
}
用户钱包通知:
public function handle(UserWalletNewTransaction $event) {
$uid = $event->transaction->user_id;
$user = User::find($uid);
// now sends alert message to the user
$oneSignal = new OneSignalService();
$oneSignal->sendNotificationToUser($user, 'New Transaction', 'You have a new transaction', 'yourwebsite.com');
}
我将通过 broadcasting, which would use websockets to instantly send the customer user an alert to their browser, in which you could then display a popup of some sort. You could install Laravel Echo Server, but to keep things simple you can use Pusher 来解决这个问题。按照指南在您的网站前端安装。
然后,创建一个特定于客户用户“transaction.created.{{USER ID}}”的私人频道,并在您的前端收听它。
在 Laravel 中,您将通过 composer 安装 PHP Pusher SDK。
然后在您的 .env 文件集中:
BROADCAST_DRIVER=pusher
接下来,在 Laravel 的路由目录中打开 channels.php 并添加:
Broadcast::channel('transaction.created.{id}', function ($user, $id) {
return (int) $user->id === (int) $id;
});
这将验证您的用户对私人频道的身份验证。
创建一个 Laravel 事件:
<?php
namespace App\Events;
use App\User;
use Illuminate\Broadcasting\Channel;
use Illuminate\Broadcasting\InteractsWithSockets;
use Illuminate\Broadcasting\PresenceChannel;
use Illuminate\Broadcasting\PrivateChannel;
use Illuminate\Contracts\Broadcasting\ShouldBroadcastNow;
use Illuminate\Foundation\Events\Dispatchable;
use Illuminate\Queue\SerializesModels;
class TransactionCreated implements ShouldBroadcastNow
{
use Dispatchable, InteractsWithSockets, SerializesModels;
public $user = null;
public $transaction = null;
/**
* Create a new event instance.
*
* @return void
*/
public function __construct(User $user, UserWalletTransaction $transaction)
{
$this->user = $user;
$this->transaction = $transaction;
}
public function broadcastWith(): array
{
return $this->transaction->toArray(); //Or whatever information you want to send to the front end
}
public function broadcastAs(): string
{
return 'TransactionCreated';
}
/**
* Get the channels the event should broadcast on.
*
* @return Channel|array
*/
public function broadcastOn()
{
return new PrivateChannel('transaction.created.' . $this->user->id);
}
}
从 UserWalletNotification 触发事件:
public function handle(UserWalletNewTransaction $event) {
$uid = $event->transaction->user_id;
$user = User::find($uid);
// now sends alert message to the user
event(new TransactionCreated($user, $event->transaction));
}
最后,当您的私人频道的回调函数被点击时,创建某种弹出窗口并将其显示在前端。
如果您需要更多帮助,请随时发表评论。