mirror of
https://git.imnavajas.es/jjimenez/erp-imprimelibros.git
synced 2026-01-13 00:48:49 +00:00
235 lines
9.6 KiB
Java
235 lines
9.6 KiB
Java
package com.imprimelibros.erp.externalApi;
|
|
|
|
import org.springframework.beans.factory.annotation.Value;
|
|
import org.springframework.http.*;
|
|
import org.springframework.stereotype.Service;
|
|
import org.springframework.web.client.HttpClientErrorException;
|
|
import org.springframework.web.client.RestTemplate;
|
|
|
|
import com.fasterxml.jackson.core.type.TypeReference;
|
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
|
|
|
import com.fasterxml.jackson.core.JsonProcessingException;
|
|
import com.fasterxml.jackson.databind.JsonNode;
|
|
import com.imprimelibros.erp.configuracion.margenes_presupuestos.MargenPresupuesto;
|
|
import com.imprimelibros.erp.configuracion.margenes_presupuestos.MargenPresupuestoDao;
|
|
import com.imprimelibros.erp.presupuesto.dto.Presupuesto.TipoCubierta;
|
|
import com.imprimelibros.erp.presupuesto.dto.Presupuesto.TipoEncuadernacion;
|
|
|
|
import java.util.Map;
|
|
import java.util.HashMap;
|
|
import java.util.List;
|
|
import java.util.function.Supplier;
|
|
|
|
@Service
|
|
public class skApiClient {
|
|
|
|
@Value("${safekat.api.url}")
|
|
private String skApiUrl;
|
|
|
|
private final AuthService authService;
|
|
private final RestTemplate restTemplate;
|
|
private final MargenPresupuestoDao margenPresupuestoDao;
|
|
|
|
public skApiClient(AuthService authService, MargenPresupuestoDao margenPresupuestoDao) {
|
|
this.authService = authService;
|
|
this.restTemplate = new RestTemplate();
|
|
this.margenPresupuestoDao = margenPresupuestoDao;
|
|
}
|
|
|
|
public String getPrice(Map<String, Object> requestBody, TipoEncuadernacion tipoEncuadernacion,
|
|
TipoCubierta tipoCubierta) {
|
|
return performWithRetry(() -> {
|
|
String url = this.skApiUrl + "api/calcular";
|
|
|
|
HttpHeaders headers = new HttpHeaders();
|
|
headers.setContentType(MediaType.APPLICATION_JSON);
|
|
headers.setBearerAuth(authService.getToken());
|
|
|
|
HttpEntity<Map<String, Object>> entity = new HttpEntity<>(requestBody, headers);
|
|
|
|
ResponseEntity<String> response = restTemplate.exchange(
|
|
url,
|
|
HttpMethod.POST,
|
|
entity,
|
|
String.class);
|
|
|
|
try {
|
|
Map<String, Object> responseBody = new ObjectMapper().readValue(
|
|
response.getBody(),
|
|
new TypeReference<Map<String, Object>>() {
|
|
});
|
|
|
|
ObjectMapper mapper = new ObjectMapper();
|
|
|
|
if (responseBody.get("error") == null) {
|
|
Object dataObj = responseBody.get("data");
|
|
|
|
if (dataObj instanceof Map) {
|
|
@SuppressWarnings("unchecked")
|
|
Map<String, Object> data = (Map<String, Object>) dataObj;
|
|
|
|
List<Integer> tiradas = mapper.convertValue(
|
|
data.get("tiradas"), new TypeReference<List<Integer>>() {
|
|
});
|
|
List<Double> precios = mapper.convertValue(
|
|
data.get("precios"), new TypeReference<List<Double>>() {
|
|
});
|
|
|
|
for (int i = 0; i < tiradas.size(); i++) {
|
|
int tirada = tiradas.get(i);
|
|
|
|
MargenPresupuesto margen = margenPresupuestoDao.findByTipoAndTirada(
|
|
tipoEncuadernacion, tipoCubierta, tirada);
|
|
|
|
if (margen != null) {
|
|
double margenValue = calcularMargen(
|
|
tirada,
|
|
margen.getTiradaMin(),
|
|
margen.getTiradaMax(),
|
|
margen.getMargenMax(),
|
|
margen.getMargenMin());
|
|
double nuevoPrecio = precios.get(i) * (1 + margenValue / 100.0);
|
|
precios.set(i, Math.round(nuevoPrecio * 10000.0) / 10000.0); // redondear a 2 decimales
|
|
} else {
|
|
System.out.println("No se encontró margen para tirada " + tirada);
|
|
}
|
|
}
|
|
|
|
// <-- Clave: sustituir la lista en el map que se devuelve
|
|
data.put("precios", precios);
|
|
// (tiradas no cambia, pero si la modificases: data.put("tiradas", tiradas);)
|
|
}
|
|
|
|
return mapper.writeValueAsString(Map.of("data", responseBody.get("data")));
|
|
} else {
|
|
return "{\"error\": 1}";
|
|
}
|
|
|
|
} catch (JsonProcessingException e) {
|
|
e.printStackTrace();
|
|
return "{\"error\": 1}";
|
|
}
|
|
});
|
|
}
|
|
|
|
public Integer getMaxSolapas(Map<String, Object> requestBody) {
|
|
try {
|
|
String jsonResponse = performWithRetry(() -> {
|
|
String url = this.skApiUrl + "api/calcular-solapas";
|
|
|
|
HttpHeaders headers = new HttpHeaders();
|
|
headers.setContentType(MediaType.APPLICATION_JSON);
|
|
headers.setBearerAuth(authService.getToken()); // token actualizado
|
|
|
|
Map<String, Object> data = new HashMap<>();
|
|
data.put("clienteId", requestBody.get("clienteId"));
|
|
data.put("tamanio", requestBody.get("tamanio"));
|
|
data.put("tirada", requestBody.get("tirada"));
|
|
data.put("paginas", requestBody.get("paginas"));
|
|
data.put("paginasColor", requestBody.get("paginasColor"));
|
|
data.put("papelInteriorDiferente", 0);
|
|
data.put("paginasCuadernillo", requestBody.get("paginasCuadernillo"));
|
|
data.put("tipo", requestBody.get("tipo"));
|
|
data.put("isColor", requestBody.get("isColor"));
|
|
data.put("isHq", requestBody.get("isHq"));
|
|
data.put("interior", requestBody.get("interior"));
|
|
|
|
HttpEntity<Map<String, Object>> entity = new HttpEntity<>(data, headers);
|
|
|
|
ResponseEntity<String> response = restTemplate.exchange(
|
|
url,
|
|
HttpMethod.POST,
|
|
entity,
|
|
String.class);
|
|
|
|
return response.getBody();
|
|
});
|
|
|
|
ObjectMapper mapper = new ObjectMapper();
|
|
JsonNode root = mapper.readTree(jsonResponse);
|
|
|
|
if (root.get("data") == null || !root.get("data").isInt()) {
|
|
throw new RuntimeException("Respuesta inesperada de calcular-solapas: " + jsonResponse);
|
|
}
|
|
|
|
return root.get("data").asInt();
|
|
|
|
} catch (JsonProcessingException e) {
|
|
// Fallback al 80% del ancho
|
|
Map<String, Object> tamanio = new ObjectMapper().convertValue(
|
|
requestBody.get("tamanio"),
|
|
new TypeReference<Map<String, Object>>() {
|
|
});
|
|
|
|
if (tamanio == null || tamanio.get("ancho") == null)
|
|
throw new RuntimeException("Tamaño no válido en la solicitud: " + requestBody);
|
|
else {
|
|
int ancho = (int) tamanio.get("ancho");
|
|
return (int) Math.floor(ancho * 0.8); // 80% del ancho
|
|
}
|
|
}
|
|
}
|
|
|
|
public Double getRetractilado(Map<String, Object> requestBody) {
|
|
|
|
String value = performWithRetry(() -> {
|
|
String url = this.skApiUrl + "api/calcular-retractilado";
|
|
|
|
HttpHeaders headers = new HttpHeaders();
|
|
headers.setContentType(MediaType.APPLICATION_JSON);
|
|
headers.setBearerAuth(authService.getToken());
|
|
|
|
HttpEntity<Map<String, Object>> entity = new HttpEntity<>(requestBody, headers);
|
|
|
|
ResponseEntity<String> response = restTemplate.exchange(
|
|
url,
|
|
HttpMethod.POST,
|
|
entity,
|
|
String.class);
|
|
|
|
try {
|
|
Map<String, Object> responseBody = new ObjectMapper().readValue(
|
|
response.getBody(),
|
|
new TypeReference<Map<String, Object>>() {
|
|
});
|
|
return responseBody.get("data").toString();
|
|
} catch (JsonProcessingException e) {
|
|
e.printStackTrace();
|
|
return "0.0"; // Fallback en caso de error
|
|
}
|
|
});
|
|
try {
|
|
return Double.parseDouble(value);
|
|
} catch (NumberFormatException e) {
|
|
throw new RuntimeException("Error al parsear el valor de retractilado: " + value, e);
|
|
}
|
|
}
|
|
|
|
/******************
|
|
* PRIVATE METHODS
|
|
******************/
|
|
private String performWithRetry(Supplier<String> request) {
|
|
try {
|
|
return request.get();
|
|
} catch (HttpClientErrorException.Unauthorized e) {
|
|
// Token expirado, renovar y reintentar
|
|
authService.invalidateToken();
|
|
try {
|
|
return request.get(); // segundo intento
|
|
} catch (HttpClientErrorException ex) {
|
|
throw new RuntimeException("La autenticación ha fallado tras renovar el token.", ex);
|
|
}
|
|
}
|
|
}
|
|
|
|
private static double calcularMargen(
|
|
int tirada, int tiradaMin, int tiradaMax,
|
|
double margenMax, double margenMin) {
|
|
if (tirada <= tiradaMin)
|
|
return margenMax;
|
|
if (tirada >= tiradaMax)
|
|
return margenMin;
|
|
return margenMax - ((double) (tirada - tiradaMin) / (tiradaMax - tiradaMin)) * (margenMax - margenMin);
|
|
}
|
|
} |