feat(logging): Implement database logging with app_log table

- Created migration to set up app_log table for storing application logs.
- Added AppLog entity and repository for ORM handling of logs.
- Developed DbLogger service to persist logs of level WARNING and above to the database while maintaining existing logging behavior.
- Implemented tests for admin log retrieval and DbLogger functionality to ensure proper logging behavior.
- Enhanced logging context sanitization for better error tracking.
This commit is contained in:
hamed
2026-06-29 20:01:03 +03:30
parent 830f7e8d0c
commit 803196108c
38 changed files with 3284 additions and 618 deletions
+6 -2
View File
@@ -3,6 +3,7 @@
namespace App\Sms\Provider;
use App\Config\Repository\SiteConfigRepository;
use Psr\Log\LoggerInterface;
use Symfony\Contracts\HttpClient\HttpClientInterface;
class KavehNegarProvider implements SmsProviderInterface
@@ -12,6 +13,7 @@ class KavehNegarProvider implements SmsProviderInterface
public function __construct(
private readonly HttpClientInterface $httpClient,
private readonly SiteConfigRepository $configRepo,
private readonly LoggerInterface $logger,
// Nullable: env `%env(default::KAVENEGAR_API_KEY)%` resolves to null when unset
// (the real key normally comes from DB site config below, not env).
private readonly ?string $apiKey = null,
@@ -38,7 +40,8 @@ class KavehNegarProvider implements SmsProviderInterface
);
$data = $resp->toArray();
return ($data['return']['status'] ?? 0) === 200;
} catch (\Throwable) {
} catch (\Throwable $e) {
$this->logger->error(sprintf('SMS send failed (kavenegar): %s @ %s:%d', $e->getMessage(), $e->getFile(), $e->getLine()), ['exception' => $e, 'mobile' => $mobile]);
return false;
}
}
@@ -58,7 +61,8 @@ class KavehNegarProvider implements SmsProviderInterface
);
$data = $resp->toArray();
return ($data['return']['status'] ?? 0) === 200;
} catch (\Throwable) {
} catch (\Throwable $e) {
$this->logger->error(sprintf('SMS sendTemplate failed (kavenegar): %s @ %s:%d', $e->getMessage(), $e->getFile(), $e->getLine()), ['exception' => $e, 'mobile' => $mobile, 'template' => $templateCode]);
return false;
}
}