fix git
This commit is contained in:
@@ -1,163 +0,0 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace App\Http\Controllers\Git;
|
||||
|
||||
use Illuminate\Http\JsonResponse;
|
||||
use Illuminate\Http\Request;
|
||||
use Illuminate\Routing\Controller;
|
||||
use Illuminate\Support\Carbon;
|
||||
use Illuminate\Support\Facades\Log;
|
||||
use Modules\Helpdesk\Models\GitCommit;
|
||||
|
||||
final class GiteaWebhookController extends Controller
|
||||
{
|
||||
/**
|
||||
* Handle an incoming Gitea webhook delivery.
|
||||
*/
|
||||
public function __invoke(Request $request): JsonResponse
|
||||
{
|
||||
Log::info('Gitea webhook endpoint hit.', [
|
||||
'event' => $request->header('X-Gitea-Event'),
|
||||
'github_event' => $request->header('X-GitHub-Event'),
|
||||
'delivery' => $request->header('X-Gitea-Delivery'),
|
||||
'authorization_present' => $request->headers->has('Authorization'),
|
||||
'signature_present' => $request->headers->has('X-Gitea-Signature'),
|
||||
]);
|
||||
|
||||
$authResponse = $this->validateAuthorization($request);
|
||||
|
||||
if ($authResponse instanceof JsonResponse) {
|
||||
return $authResponse;
|
||||
}
|
||||
|
||||
$signatureResponse = $this->validateSignature($request);
|
||||
|
||||
if ($signatureResponse instanceof JsonResponse) {
|
||||
return $signatureResponse;
|
||||
}
|
||||
|
||||
$event = (string) ($request->header('X-Gitea-Event') ?: $request->header('X-GitHub-Event'));
|
||||
$payload = $request->json()->all();
|
||||
|
||||
if ($event !== 'push') {
|
||||
Log::info('Gitea webhook ignored.', [
|
||||
'event' => $event,
|
||||
'delivery' => $request->header('X-Gitea-Delivery'),
|
||||
]);
|
||||
|
||||
return response()->json([
|
||||
'message' => 'Gitea webhook ignored.',
|
||||
'event' => $event,
|
||||
]);
|
||||
}
|
||||
|
||||
$commits = data_get($payload, 'commits', []);
|
||||
|
||||
Log::info('Gitea push webhook received.', [
|
||||
'repository' => data_get($payload, 'repository.full_name'),
|
||||
'ref' => data_get($payload, 'ref'),
|
||||
'branch' => str_replace('refs/heads/', '', (string) data_get($payload, 'ref')),
|
||||
'before' => data_get($payload, 'before'),
|
||||
'after' => data_get($payload, 'after'),
|
||||
'commit_count' => is_countable($commits) ? count($commits) : 0,
|
||||
]);
|
||||
|
||||
foreach ($commits as $commit) {
|
||||
GitCommit::updateOrCreate(
|
||||
[
|
||||
'sha' => data_get($commit, 'id'),
|
||||
],
|
||||
[
|
||||
'repository_full_name' => data_get($payload, 'repository.full_name'),
|
||||
'repository_name' => data_get($payload, 'repository.name'),
|
||||
'branch' => str_replace(
|
||||
'refs/heads/',
|
||||
'',
|
||||
(string) data_get($payload, 'ref'),
|
||||
),
|
||||
'author_name' => data_get($commit, 'author.name'),
|
||||
'author_email' => data_get($commit, 'author.email'),
|
||||
'message' => data_get($commit, 'message'),
|
||||
'commit_url' => data_get($commit, 'url'),
|
||||
'committed_at' => data_get($commit, 'timestamp')
|
||||
? Carbon::parse(data_get($commit, 'timestamp'))
|
||||
: now(),
|
||||
'payload' => $commit,
|
||||
],
|
||||
);
|
||||
|
||||
Log::info('Git commit stored.', [
|
||||
'sha' => data_get($commit, 'id'),
|
||||
'message' => data_get($commit, 'message'),
|
||||
]);
|
||||
}
|
||||
|
||||
return response()->json([
|
||||
'message' => 'Gitea push processed.',
|
||||
'repository' => data_get($payload, 'repository.full_name'),
|
||||
'branch' => str_replace('refs/heads/', '', (string) data_get($payload, 'ref')),
|
||||
'commit_count' => is_countable($commits) ? count($commits) : 0,
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Validate the optional Gitea Authorization header.
|
||||
*/
|
||||
private function validateAuthorization(Request $request): ?JsonResponse
|
||||
{
|
||||
$expected = (string) config('services.gitea.webhook_authorization');
|
||||
|
||||
if ($expected === '') {
|
||||
return null;
|
||||
}
|
||||
|
||||
$actual = (string) $request->header('Authorization');
|
||||
|
||||
if (hash_equals($expected, $actual)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
Log::warning('Rejected Gitea webhook because Authorization header was invalid.', [
|
||||
'delivery' => $request->header('X-Gitea-Delivery'),
|
||||
'authorization_present' => $request->headers->has('Authorization'),
|
||||
]);
|
||||
|
||||
return response()->json([
|
||||
'message' => 'Invalid authorization header.',
|
||||
], 403);
|
||||
}
|
||||
|
||||
/**
|
||||
* Validate the optional Gitea HMAC SHA-256 signature.
|
||||
*/
|
||||
private function validateSignature(Request $request): ?JsonResponse
|
||||
{
|
||||
$secret = (string) config('services.gitea.webhook_secret');
|
||||
|
||||
if ($secret === '') {
|
||||
return null;
|
||||
}
|
||||
|
||||
$payload = $request->getContent();
|
||||
$signature = (string) $request->header('X-Gitea-Signature');
|
||||
|
||||
$expected = hash_hmac('sha256', $payload, $secret);
|
||||
|
||||
if ($signature !== '' && hash_equals($expected, $signature)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
Log::warning('Rejected Gitea webhook because signature was invalid.', [
|
||||
'delivery' => $request->header('X-Gitea-Delivery'),
|
||||
'signature_present' => $request->headers->has('X-Gitea-Signature'),
|
||||
'expected' => $expected,
|
||||
'actual' => $signature,
|
||||
]);
|
||||
|
||||
return response()->json([
|
||||
'message' => 'Invalid Gitea signature.',
|
||||
], 403);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user