Para integrar um motor de geração de imagens em sistemas de e-commerec, certifique-se de que seu ambiente atenda a estes requisitos:
- JDK 11 ou superior
- Spring Boot 2.7+
- Maven 3.6+ ou Gradle 7+
- Memória mínima recomendada de 8GB
Adicione as dependências necessárias no arquivo pom.xml:
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
</dependency>
<dependency>
<groupId>com.squareup.okhttp3</groupId>
<artifactId>okhttp</artifactId>
<version>4.10.0</version>
</dependency>
</dependencies>
Configure os parâmetros de conexão no application.yml:
image:
generation:
base-url: http://servico-gerador:8080
api-key: chave-api-aqui
timeout: 30000
- Implementação do Cliente de Serviço
Crie uma classe para lidar com a comunicação com a API de geração de imagens:
@Service
public class ImageApiClient {
@Value("${image.generation.base-url}")
private String apiEndpoint;
@Value("${image.generation.api-key}")
private String authenticationKey;
private final OkHttpClient httpEngine;
public ImageApiClient() {
this.httpEngine = new OkHttpClient.Builder()
.connectTimeout(25, TimeUnit.SECONDS)
.readTimeout(25, TimeUnit.SECONDS)
.build();
}
public String requestProductImage(ImagePayload payload) {
try {
ObjectMapper jsonMapper = new ObjectMapper();
String requestBody = jsonMapper.writeValueAsString(payload);
Request httpRequest = new Request.Builder()
.url(apiEndpoint + "/v1/create-image")
.post(RequestBody.create(requestBody, MediaType.parse("application/json")))
.addHeader("Authorization", "Bearer " + authenticationKey)
.build();
try (Response apiResponse = httpEngine.newCall(httpRequest).execute()) {
if (apiResponse.isSuccessful()) {
String responseBody = apiResponse.body().string();
ImageResult result = jsonMapper.readValue(responseBody, ImageResult.class);
return result.getDownloadLink();
} else {
throw new RuntimeException("Falha na geração: " + apiResponse.code());
}
}
} catch (Exception ex) {
throw new RuntimeException("Erro na chamada da API", ex);
}
}
}
Defina a estrutura de requisição:
@Data
@Builder
public class ImagePayload {
private String productName;
private String productDetails;
private String aestheticStyle;
private Integer dimensionsWidth;
private Integer dimensionsHeight;
public ImagePayload(String productName, String productDetails) {
this.productName = productName;
this.productDetails = productDetails;
this.dimensionsWidth = 768;
this.dimensionsHeight = 768;
this.aestheticStyle = "standard";
}
}
- Integração com Fluxo de Produtos
Incorpoer a geração de imagens ao processo de cadasrto de produtos:
@Service
public class CatalogImageService {
private final ImageApiClient imageClient;
private final CatalogRepository catalogRepo;
public CatalogImageService(ImageApiClient imageClient, CatalogRepository catalogRepo) {
this.imageClient = imageClient;
this.catalogRepo = catalogRepo;
}
@Async
public void enrichProductWithImage(Long catalogId) {
CatalogItem item = catalogRepo.findById(catalogId)
.orElseThrow(() -> new NoSuchElementException("Item não encontrado"));
ImagePayload payload = new ImagePayload(item.getTitle(), item.getSummary());
String generatedUrl = imageClient.requestProductImage(payload);
item.setPrimaryImageUrl(generatedUrl);
catalogRepo.save(item);
}
}
- Processamento em Lote e Otimização
Para operações de alto volume, implemente processamento paralelo:
@Service
public class BulkImageProcessor {
private final ImageApiClient imageClient;
private final ExecutorService workerPool;
public BulkImageProcessor(ImageApiClient imageClient) {
this.imageClient = imageClient;
this.workerPool = Executors.newFixedThreadPool(8);
}
public List<String> processInParallel(List<ImagePayload> payloads) {
List<Future<String>> futures = payloads.stream()
.map(payload -> workerPool.submit(() -> imageClient.requestProductImage(payload)))
.collect(Collectors.toList());
return futures.stream()
.map(future -> {
try {
return future.get();
} catch (Exception e) {
throw new RuntimeException("Falha no processamento", e);
}
})
.collect(Collectors.toList());
}
}
Utilize caching para reduzir chamadas repetidas à API:
@Service
public class ImageCachingLayer {
private final ImageApiClient imageClient;
private final LoadingCache<String, String> cacheStore;
public ImageCachingLayer(ImageApiClient imageClient) {
this.imageClient = imageClient;
this.cacheStore = Caffeine.newBuilder()
.maximumSize(200)
.expireAfterWrite(12, TimeUnit.HOURS)
.build(key -> generateImage(key));
}
public String getImageWithCache(ImagePayload payload) {
String cacheKey = payload.getProductName() + "|" + payload.getAestheticStyle();
return cacheStore.get(cacheKey);
}
private String generateImage(String cacheKey) {
String[] parts = cacheKey.split("\\|");
ImagePayload payload = new ImagePayload(parts[0], "");
payload.setAestheticStyle(parts[1]);
return imageClient.requestProductImage(payload);
}
}