当我使用 laravel 修补程序会话 fiddle 与观察者 class 中的模型时,有没有办法捕捉?

Is there a way to catch when I'm using a laravel tinker session to fiddle with the Models in an Observer class?

我有一个 Observer 设置来监听 Model 的事件,以保持我的 Controller 清洁日志消息。我的实现如下:

首先,一个只做它应该做的事情的存储方法。根据有效参数创建并保存新模型。

# app/Http/Controllers/ExampleController.php
namespace App\Http\Controllers;

use App\Http\Requests\StoreExample;
use App\Example;

class ExampleController extends Controller
{
    public function __construct()
    {
        $this->middleware('auth');
    }

    /**
     * Create and save an Example from validated form parameters.
     * @param  App\Http\Requests\StoreExample  $request
     */
    public function store(StoreExample $request)
    {
        Example::create($request->validated());

        return back();
    }
}

StoreExample 表单请求并不重要。它只是验证并检查一个门以授权该操作。

我设置的 Observer 会记录此操作。

# app/Observers/ExampleObserver.php
namespace App\Observers;

use App\Example;

class ExampleObserver
{
    public function created(Example $example): void
    {
        \Log::info(auth()->id()." (".auth()->user()->full_name.") has created Example with params:\n{$example}");
    }
}

我遇到的问题是我的日志依赖于要设置的 auth() 对象的方式。鉴于 auth 中间件和它必须检查以存储示例的门,来宾用户无法触发此代码。

但是,我确实喜欢在我的本地和暂存环境中使用 tinker 来检查站点的行为,但这可能会引发错误(好吧,PHP notice 更准确)因为我可以在不经过身份验证的情况下创建 Example 模型,并且记录器将尝试从非对象 auth()->user().

中获取 属性 full_name

所以我的问题如下:当我专门使用 Laravel tinker 会话来处理我在 Observer class 中的模型时,有没有办法捕获?

好的,回答我自己的问题:一种方法。它需要使用 Request 对象。 由于观察者不会自己处理请求,所以我在构造函数中注入了一个。 request() 可以代替,因此不需要DI。

为什么请求很重要?

因为请求对象有一个可访问的 $server 属性,其中包含我想要的信息。这是我通过返回一个 dd($request->server) 得到的相关信息(我不会粘贴整个东西。我的 Request 的 ServerBag 有超过 100 个属性!)

Symfony\Component\HttpFoundation\ServerBag {#37
  #parameters: array:123 [
    "SERVER_NAME" => "localhost"
    "SERVER_PORT" => 8000
    "HTTP_HOST" => "localhost:8000"
    "HTTP_USER_AGENT" => "Symfony"   // Relevant
    "REMOTE_ADDR" => "127.0.0.1"
    "SCRIPT_NAME" => "artisan"       // Relevant
    "SCRIPT_FILENAME" => "artisan"   // Relevant
    "PHP_SELF" => "artisan"          // Relevant
    "PATH_TRANSLATED" => "artisan"   // Relevant
    "argv" => array:2 [              // Relevant
      0 => "artisan"
      1 => "tinker"
    ]
    "argc" => 2
  ]
}

所以我可以使用 $request->server('attribute')(returns $request->server->attributenull 过滤所有这些属性,因此没有访问未定义 属性 的风险).我也可以做 $request->server->has('attribute') (returns truefalse)

# app/Observers/ExampleObserver.php
namespace App\Observers;

use App\Example;

class ExampleObserver
{
    /* Since we can use request(), there's no need to inject a Request into the constructor
    protected $request;

    public function __construct(Request $request)
    {
        $this->request = $request;
    }
    */

    public function created(Example $example): void
    {
        \Log::info($this->getUserInfo()." has created Example with params:\n{$example}");
    }

    private function getUserInfo(): string
    {
        // My logic here. 
    }
}