69 lines
2.0 KiB
PHP
69 lines
2.0 KiB
PHP
<?php
|
|
|
|
namespace App\Console\Commands;
|
|
|
|
use App\Services\Graph\GraphClientInterface;
|
|
use Illuminate\Console\Command;
|
|
|
|
class GraphContractCheck extends Command
|
|
{
|
|
protected $signature = 'graph:contract:check {--tenant=}';
|
|
|
|
protected $description = 'Validate Graph contract registry against live endpoints (lightweight probes)';
|
|
|
|
public function handle(GraphClientInterface $graph): int
|
|
{
|
|
$contracts = config('graph_contracts.types', []);
|
|
|
|
if (empty($contracts)) {
|
|
$this->warn('No graph contracts configured.');
|
|
|
|
return self::SUCCESS;
|
|
}
|
|
|
|
$tenant = $this->option('tenant');
|
|
$failures = 0;
|
|
|
|
foreach ($contracts as $type => $contract) {
|
|
$resource = $contract['resource'] ?? null;
|
|
$select = $contract['allowed_select'] ?? [];
|
|
$expand = $contract['allowed_expand'] ?? [];
|
|
|
|
if (! $resource) {
|
|
$this->error("[$type] missing resource path");
|
|
$failures++;
|
|
|
|
continue;
|
|
}
|
|
|
|
$query = array_filter([
|
|
'$top' => 1,
|
|
'$select' => $select,
|
|
'$expand' => $expand,
|
|
]);
|
|
|
|
$response = $graph->request('GET', $resource, [
|
|
'query' => $query,
|
|
'tenant' => $tenant,
|
|
]);
|
|
|
|
if ($response->failed()) {
|
|
$code = $response->meta['error_code'] ?? $response->status;
|
|
$message = $response->meta['error_message'] ?? ($response->errors[0]['message'] ?? $response->errors[0] ?? 'unknown');
|
|
$this->error("[$type] drift or capability issue ({$code}): {$message}");
|
|
$failures++;
|
|
|
|
continue;
|
|
}
|
|
|
|
if (! empty($response->warnings)) {
|
|
$this->warn("[$type] completed with warnings: ".implode('; ', $response->warnings));
|
|
} else {
|
|
$this->info("[$type] OK");
|
|
}
|
|
}
|
|
|
|
return $failures > 0 ? self::FAILURE : self::SUCCESS;
|
|
}
|
|
}
|