Linux SRV-16 6.18.44-paas #1 SMP PREEMPT_DYNAMIC Thu Aug 13 10:08:12 UTC 2026 x86_64
/
proc
/
212
/
root
/
proc
/
212
/
root
/
proc
/
self
/
root
/
proc
/
70528
/
cwd
/
src
/
Service
/
//proc/212/root/proc/212/root/proc/self/root/proc/70528/cwd/src/Service/ImageGenerator.php
<?php namespace App\Service; use Symfony\Component\Mime\Part\DataPart; use Symfony\Component\Mime\Part\Multipart\FormDataPart; use Symfony\Contracts\HttpClient\HttpClientInterface; class ImageGenerator { private $openaiApiKey; private $httpClient; public function __construct( HttpClientInterface $httpClient, string $openaiApiKey ) { $this->httpClient = $httpClient; $this->openaiApiKey = $openaiApiKey; } /** Génération et retouche partagent le même modèle : une retouche repart d'une image générée. */ public const MODEL = 'gpt-image-2'; public const REQUEST_TIMEOUT = 300; /** Formats acceptés : carré, portrait, paysage. */ public const SIZE_SQUARE = '1024x1024'; public const SIZE_PORTRAIT = '1024x1536'; public const SIZE_LANDSCAPE = '1536x1024'; /** * Génère une image à partir d'un prompt. * * Le format demandé doit suivre les proportions de l'emplacement à remplir : * une image carrée placée sur un support portrait est rognée sur les côtés. * * Retourne un chemin de fichier temporaire contenant l'image générée. */ public function generate(string $prompt, string $size = self::SIZE_SQUARE): string { $response = $this->httpClient->request( 'POST', 'https://api.openai.com/v1/images/generations', [ 'headers' => [ 'Authorization' => 'Bearer ' . $this->openaiApiKey, 'Content-Type' => 'application/json', ], 'json' => [ 'model' => self::MODEL, 'prompt' => $prompt, 'size' => $size, 'quality' => 'high', ], 'timeout' => self::REQUEST_TIMEOUT, ] ); return $this->storeImage($response->toArray()); } /** * Retouche une image existante à partir d'un prompt : l'image de départ est * conservée au maximum ("input_fidelity"), seules les corrections demandées * sont appliquées (texte, cadrage, couleurs...). * * Retourne un chemin de fichier temporaire contenant l'image corrigée. */ public function edit(string $imagePath, string $prompt, string $size = self::SIZE_SQUARE): string { $formData = new FormDataPart([ 'model' => self::MODEL, 'prompt' => $prompt, 'size' => $size, 'quality' => 'high', 'input_fidelity' => 'high', 'image' => DataPart::fromPath($imagePath), ]); $response = $this->httpClient->request( 'POST', 'https://api.openai.com/v1/images/edits', [ 'headers' => array_merge( $formData->getPreparedHeaders()->toArray(), ['Authorization' => 'Bearer ' . $this->openaiApiKey] ), 'body' => $formData->bodyToIterable(), 'timeout' => self::REQUEST_TIMEOUT, ] ); return $this->storeImage($response->toArray()); } /** * Écrit l'image renvoyée par l'API dans un fichier temporaire. */ private function storeImage(array $data): string { if (!isset($data['data'][0]['b64_json'])) { throw new \RuntimeException( 'Impossible de récupérer l’image générée.' ); } $imageBinary = base64_decode( $data['data'][0]['b64_json'] ); if ($imageBinary === false) { throw new \RuntimeException( 'Erreur de décodage de l’image générée.' ); } $filename = sprintf( '%s/generated_%s.png', sys_get_temp_dir(), bin2hex(random_bytes(8)) ); file_put_contents($filename, $imageBinary); return $filename; } }