TenantAtlas/apps/platform/app/Services/Graph/GraphLogger.php
ahmido ce0615a9c1 Spec 182: relocate Laravel platform to apps/platform (#213)
## Summary
- move the Laravel application into `apps/platform` and keep the repository root for orchestration, docs, and tooling
- update the local command model, Sail/Docker wiring, runtime paths, and ignore rules around the new platform location
- add relocation quickstart/contracts plus focused smoke coverage for bootstrap, command model, routes, and runtime behavior

## Validation
- `cd apps/platform && ./vendor/bin/sail artisan test --compact tests/Feature/PlatformRelocation`
- integrated browser smoke validated `/up`, `/`, `/admin`, `/admin/choose-workspace`, and tenant route semantics for `200`, `403`, and `404`

## Remaining Rollout Checks
- validate Dokploy build context and working-directory assumptions against the new `apps/platform` layout
- confirm web, queue, and scheduler processes all start from the expected working directory in staging/production
- verify no legacy volume mounts or asset-publish paths still point at the old root-level `public/` or `storage/` locations

Co-authored-by: Ahmed Darrazi <ahmed.darrazi@live.de>
Reviewed-on: #213
2026-04-08 08:40:47 +00:00

90 lines
3.0 KiB
PHP

<?php
namespace App\Services\Graph;
use Illuminate\Support\Facades\Log;
use Illuminate\Support\Str;
class GraphLogger
{
public function logRequest(string $action, array $context = []): void
{
$payload = [
'action' => $action,
'method' => $context['method'] ?? null,
'endpoint' => $context['endpoint'] ?? null,
'full_path' => $context['full_path'] ?? null,
'query' => $context['query'] ?? null,
'tenant' => $context['tenant'] ?? null,
'client_request_id' => $context['client_request_id'] ?? null,
];
Log::info('graph.request', $this->filter($payload));
}
public function logResponse(string $action, GraphResponse $response, array $context = []): void
{
$payload = [
'action' => $action,
'status' => $response->status,
'success' => $response->success,
'warnings' => $response->warnings,
'method' => $context['method'] ?? $response->meta['method'] ?? null,
'endpoint' => $context['endpoint'] ?? $response->meta['path'] ?? null,
'full_path' => $context['full_path'] ?? $response->meta['full_path'] ?? null,
'tenant' => $context['tenant'] ?? $response->meta['tenant'] ?? null,
'request_id' => $response->meta['request_id'] ?? null,
'client_request_id' => $response->meta['client_request_id'] ?? null,
];
if ($response->failed()) {
$payload['error_code'] = $response->meta['error_code'] ?? $this->firstErrorField($response->errors, 'code');
$payload['error_message'] = $response->meta['error_message'] ?? $this->firstErrorMessage($response->errors, $response->data);
$payload['response_excerpt'] = $response->meta['body_excerpt'] ?? null;
}
Log::info('graph.response', $this->filter($payload));
}
private function firstErrorField(array $errors, string $key): ?string
{
foreach ($errors as $error) {
if (is_array($error) && is_string($error[$key] ?? null)) {
return $error[$key];
}
}
return null;
}
private function firstErrorMessage(array $errors, array $data): ?string
{
$message = $data['error']['message'] ?? null;
if (is_string($message) && $message !== '') {
return $message;
}
foreach ($errors as $error) {
if (is_array($error) && is_string($error['message'] ?? null)) {
return $error['message'];
}
if (is_array($error) && is_string($error['error']['message'] ?? null)) {
return $error['error']['message'];
}
if (is_string($error) && $error !== '') {
return Str::limit($error, 500);
}
}
return null;
}
private function filter(array $payload): array
{
return array_filter($payload, static fn ($value) => $value !== null && $value !== []);
}
}