实现查询日志框架记录器,以便在正确的事务中回滚(跟踪事件)

问题描述 投票:0回答:1

这篇文章不是在寻找建议,而是在寻找本机框架中是否存在功能或方法来跟踪/记录查询执行。

我有几个数据库,我需要仔细监控这些数据库。

放弃通过委员会自动回滚解决常见错误的做法。

事实证明,现在可能存在“可接受”的错误,例如:产品从与卡车装运相关的仓库出发......这是不应该做的。

诸如在 mysql 中记录查询或这些事件以在事务正确时进行手动回滚,但它们不应该这样做,因为有人没有看到客户端发送的取消订单的电子邮件。

我想到建立一个Task对象,并基于流程的可追溯性,存储与数据库的所有交互。并在查询中进行一些逆向工程,使我可以通过按钮和选择框来识别任务并逆向它。

还控制可以找到流程可追溯性的阶段。

目前 Laravel 或 Synfony 中是否有任何原生框架选项可以实现此目的?

这不是删除数据...而是关于调整库存余额...然后如果有正向运动,我认为 Laravel/symfony ORM 有一些东西可以产生反向运动,这是加法和减法...或者甚至跟踪执行查询以了解步骤过程。

php mysql laravel symfony
1个回答
0
投票

好吧,根据我的调查,每个框架本身都有一个日志或记录器系统,可以实现记录整个过程中每个订单中发生的情况。

由于这个想法是取一个流程,并且我提到可以用任务ID来标识它,所以这个想法可以表达如下:

Symfony Logger 查询每个任务的 JSON 文件:

  1. 我们定义了一个自定义日志记录服务,将 SQL 查询记录到 JSON 文件中:
// config/services.yaml
services:
    App\Service\DatabaseLogger:
        tags:
            - { name: 'kernel.event_listener', event: 'kernel.request', method: 'onKernelRequest' }
  1. 我们创建
    DatabaseLogger
    类来记录 SQL 查询:
// src/Service/DatabaseLogger.php

namespace App\Service;

use Symfony\Component\HttpKernel\Event\RequestEvent;

class DatabaseLogger
{
    private $logDir;

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

    public function onKernelRequest(RequestEvent $event)
    {

        $request = $event->getRequest();
        $pedidoId = $request->query->get('pedido_id');

        // Here we must implement the logic to record the SQL queries in a JSON file
        $jsonLog = json_encode($event->getRequest()->attributes->all());

        // Save the JSON to a file
        file_put_contents($this->logDir.'/query_log_' . date('Y-m-d') . '.json', $jsonLog, FILE_APPEND);
    }
}
  1. 我们在您的配置文件中配置日志目录:
// config/packages/parameters.yaml
parameters:
    log_dir: '%kernel.project_dir%/var/log/task'

Laravel Logger 从每个任务查询到 JSON 文件:

  1. 我们在
    DB::listen
    文件中注册
    AppServiceProvider
    事件的监听器:
// app/Providers/AppServiceProvider.php
namespace App\Providers;

use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Log;
use Illuminate\Support\ServiceProvider;

class AppServiceProvider extends ServiceProvider
{
    public function register()
    {
        $pedidoId = request()->query('pedido_id');
        // Listener for DB::listen event
        DB::listen(function ($query) {
            $jsonLog = json_encode($query->sql);
            // Guarda el JSON en un archivo
            $logFileName = 'pedido_' . $pedidoId . '_query.log';
            Log::channel('query')->useFiles(storage_path('logs/' . $logFileName))->info($jsonLog);
        });
    }
}
  1. 在config/logging.php文件中配置日志通道:
'channels' => [
    'query' => [
        'driver' => 'single',
        'path' => storage_path('logs/query.log'),
        'level' => 'info',
    ],
    // Other logging channels...
],

根据文档,当我们在代码中使用

useFiles
动态指定日志文件的名称时,该值将被忽略,并使用我们在代码中提供的值。

注意:我还无法验证这个提案,我正在开发和实施过程中,如果一切顺利,我将在每个订单的文件中保存我在数据库中接触的内容,如果我需要取消一个订单,我将能够对该订单在数据库中修改的所有内容进行追踪。

注2:这个答案包括两个框架,我建议将其作为模块/插件发布,可以在任何需要的场景中实现。

© www.soinside.com 2019 - 2024. All rights reserved.