✨ feat(Formules.php): Ajoute relation OneToOne avec FormulesRestriction. ✨ feat(Dashboard/FormulesController.php): Gère restrictions formules et formulaire. 🎨 refactor(template/formules): Améliore interface configuration restriction formule. 🐛 fix(assets/RepeatLine.js): Corrige réinitialisation TomSelect et selects "Type". ✨ feat(assets/initTomSelect.js): Gère cache options et init TomSelect. ```
133 lines
5.0 KiB
PHP
133 lines
5.0 KiB
PHP
<?php
|
|
|
|
namespace App\Command;
|
|
|
|
use Symfony\Component\Console\Attribute\AsCommand;
|
|
use Symfony\Component\Console\Command\Command;
|
|
use Symfony\Component\Console\Input\InputInterface;
|
|
use Symfony\Component\Console\Output\OutputInterface;
|
|
use Symfony\Component\Console\Style\SymfonyStyle;
|
|
use Symfony\Component\Process\Process;
|
|
use Symfony\Component\HttpKernel\KernelInterface; // Pour le dossier projet
|
|
use Symfony\Contracts\HttpClient\HttpClientInterface;
|
|
use GeminiAPI\Client;
|
|
use GeminiAPI\Resources\Parts\TextPart;
|
|
|
|
#[AsCommand(
|
|
name: 'app:git-log-update',
|
|
description: 'Archive le dernier commit avec reformulation IA et notification Discord.',
|
|
)]
|
|
class GitSyncLogCommand extends Command
|
|
{
|
|
private HttpClientInterface $httpClient;
|
|
private string $projectDir;
|
|
|
|
// On injecte le Kernel pour le chemin du projet et HttpClient pour Discord
|
|
public function __construct(HttpClientInterface $httpClient, KernelInterface $kernel)
|
|
{
|
|
parent::__construct();
|
|
$this->httpClient = $httpClient;
|
|
$this->projectDir = $kernel->getProjectDir();
|
|
}
|
|
|
|
protected function execute(InputInterface $input, OutputInterface $output): int
|
|
{
|
|
$io = new SymfonyStyle($input, $output);
|
|
|
|
// Chemins dynamiques basés sur ProjectDir
|
|
$filePath = $this->projectDir . '/var/update.json';
|
|
$discordWebhook = 'https://discord.com/api/webhooks/1447983279902031963/O6P5oHVHFe2t2MgjFmOW-tOVrvdLf3JQDPAj8snlgKIrfGc8uJQKAHgqRJJjyoSsFYCR';
|
|
|
|
// 1. Récupération des infos Git
|
|
// On utilise $this->projectDir pour le safe.directory
|
|
$gitCmd = sprintf(
|
|
'git config --global --add safe.directory %s && git log -1 --format="%%s|%%ci|%%h"',
|
|
$this->projectDir
|
|
);
|
|
|
|
$process = Process::fromShellCommandline($gitCmd);
|
|
$process->setWorkingDirectory($this->projectDir); // On force le dossier de travail
|
|
$process->run();
|
|
|
|
if (!$process->isSuccessful()) {
|
|
$io->error("Erreur Git : " . $process->getErrorOutput());
|
|
return Command::FAILURE;
|
|
}
|
|
|
|
$outputGit = explode('|', trim($process->getOutput()));
|
|
$rawMessage = $outputGit[0] ?? '';
|
|
$commitDate = $outputGit[1] ?? date('Y-m-d H:i:s');
|
|
$commitHash = $outputGit[2] ?? 'unknown';
|
|
|
|
// 2. Détermination du TYPE (feature, fix, optimise, new)
|
|
$type = 'new';
|
|
$lowerMsg = strtolower($rawMessage);
|
|
if (preg_match('/(fix|bug|patch|correct)/', $lowerMsg)) $type = 'fix';
|
|
elseif (preg_match('/(feat|add|create|nouveau|new)/', $lowerMsg)) $type = 'feature';
|
|
elseif (preg_match('/(perf|opti|refactor|clean|speed)/', $lowerMsg)) $type = 'optimise';
|
|
|
|
// 3. Vérification anti-doublon
|
|
$data = [];
|
|
if (file_exists($filePath)) {
|
|
$data = json_decode(file_get_contents($filePath), true) ?? [];
|
|
}
|
|
|
|
if (!empty($data) && $data[0]['hash'] === $commitHash) {
|
|
$io->info("Le commit [$commitHash] est déjà à jour.");
|
|
return Command::SUCCESS;
|
|
}
|
|
|
|
// 4. Appel IA Gemini
|
|
$friendlyMessage = $rawMessage;
|
|
try {
|
|
$client = new Client("AIzaSyDTPJERlUC47bcvhZU51Lwpqb1uxXS8SIg");
|
|
$model = 'gemini-3-pro-preview';
|
|
|
|
$prompt = "Tu es un expert en communication web pour Ludik Event. Ta mission est de transformer
|
|
un message de commit technique en une note de mise à jour élégante pour ton client.
|
|
MESSAGE TECHNIQUE : \"$rawMessage\"
|
|
DIRECTIVES : Court, positif, pas de 'Voici la phrase', uniquement le résultat final.";
|
|
|
|
$response = $client->withV1BetaVersion()->generativeModel($model)->generateContent(new TextPart($prompt));
|
|
if ($response->text()) {
|
|
$friendlyMessage = trim($response->text());
|
|
}
|
|
} catch (\Exception $e) {
|
|
$io->warning("L'IA n'a pas pu traiter le message.");
|
|
}
|
|
|
|
// 5. Mise à jour du fichier JSON
|
|
$newEntry = [
|
|
'type' => $type,
|
|
'message' => $friendlyMessage,
|
|
'date' => $commitDate,
|
|
'hash' => $commitHash
|
|
];
|
|
|
|
array_unshift($data, $newEntry);
|
|
$data = array_slice($data, 0, 6);
|
|
|
|
$varDir = $this->projectDir . '/var';
|
|
if (!is_dir($varDir)) {
|
|
mkdir($varDir, 0777, true);
|
|
}
|
|
|
|
file_put_contents($filePath, json_encode($data, JSON_PRETTY_PRINT | JSON_UNESCAPED_UNICODE));
|
|
|
|
// 6. Envoi Discord
|
|
try {
|
|
$discordMessage = "📢 **Mise à jour sera prochaine mise en ligne sur votre intranet**\n\n> " . $friendlyMessage;
|
|
|
|
$this->httpClient->request('POST', $discordWebhook, [
|
|
'json' => ['content' => $discordMessage]
|
|
]);
|
|
$io->note("Notification Discord envoyée.");
|
|
} catch (\Exception $e) {
|
|
$io->error("Erreur Discord : " . $e->getMessage());
|
|
}
|
|
|
|
$io->success("Journal client mis à jour avec succès.");
|
|
return Command::SUCCESS;
|
|
}
|
|
}
|