Compare commits
No commits in common. "main" and "pranical/feature/jsonhelper-update" have entirely different histories.
main
...
pranical/f
38
.gitignore
vendored
Normal file
38
.gitignore
vendored
Normal file
@ -0,0 +1,38 @@
|
||||
target/
|
||||
!.mvn/wrapper/maven-wrapper.jar
|
||||
!**/src/main/**/target/
|
||||
!**/src/test/**/target/
|
||||
|
||||
### IntelliJ IDEA ###
|
||||
.idea/modules.xml
|
||||
.idea/jarRepositories.xml
|
||||
.idea/compiler.xml
|
||||
.idea/libraries/
|
||||
*.iws
|
||||
*.iml
|
||||
*.ipr
|
||||
|
||||
### Eclipse ###
|
||||
.apt_generated
|
||||
.classpath
|
||||
.factorypath
|
||||
.project
|
||||
.settings
|
||||
.springBeans
|
||||
.sts4-cache
|
||||
|
||||
### NetBeans ###
|
||||
/nbproject/private/
|
||||
/nbbuild/
|
||||
/dist/
|
||||
/nbdist/
|
||||
/.nb-gradle/
|
||||
build/
|
||||
!**/src/main/**/build/
|
||||
!**/src/test/**/build/
|
||||
|
||||
### VS Code ###
|
||||
.vscode/
|
||||
|
||||
### Mac OS ###
|
||||
.DS_Store
|
||||
3
.idea/.gitignore
generated
vendored
Normal file
3
.idea/.gitignore
generated
vendored
Normal file
@ -0,0 +1,3 @@
|
||||
# Default ignored files
|
||||
/shelf/
|
||||
/workspace.xml
|
||||
7
.idea/encodings.xml
generated
Normal file
7
.idea/encodings.xml
generated
Normal file
@ -0,0 +1,7 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="Encoding">
|
||||
<file url="file://$PROJECT_DIR$/src/main/java" charset="UTF-8" />
|
||||
<file url="file://$PROJECT_DIR$/src/main/resources" charset="UTF-8" />
|
||||
</component>
|
||||
</project>
|
||||
14
.idea/misc.xml
generated
Normal file
14
.idea/misc.xml
generated
Normal file
@ -0,0 +1,14 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="ExternalStorageConfigurationManager" enabled="true" />
|
||||
<component name="MavenProjectsManager">
|
||||
<option name="originalFiles">
|
||||
<list>
|
||||
<option value="$PROJECT_DIR$/pom.xml" />
|
||||
</list>
|
||||
</option>
|
||||
</component>
|
||||
<component name="ProjectRootManager" version="2" languageLevel="JDK_17" default="true" project-jdk-name="temurin-17" project-jdk-type="JavaSDK">
|
||||
<output url="file://$PROJECT_DIR$/out" />
|
||||
</component>
|
||||
</project>
|
||||
6
.idea/vcs.xml
generated
Normal file
6
.idea/vcs.xml
generated
Normal file
@ -0,0 +1,6 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="VcsDirectoryMappings">
|
||||
<mapping directory="" vcs="Git" />
|
||||
</component>
|
||||
</project>
|
||||
10
CHANGELOG.md
Normal file
10
CHANGELOG.md
Normal file
@ -0,0 +1,10 @@
|
||||
# Changelog
|
||||
|
||||
Todos los cambios notables en este proyecto se documentarán en este archivo.
|
||||
|
||||
El formato se basa en [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
|
||||
y este proyecto se adhiere a [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
||||
|
||||
## [UNRELEASE]
|
||||
|
||||
- Base inicial commons nativo (Java)
|
||||
21
LICENCE
Normal file
21
LICENCE
Normal file
@ -0,0 +1,21 @@
|
||||
MIT License
|
||||
|
||||
Copyright (c) 2024 Banesco Banco Universal, C.A.
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
11
README.md
11
README.md
@ -1,3 +1,10 @@
|
||||
# commons-plain-java
|
||||
|
||||
commons en Java puro para usar con APIs Quarkus y/o BIAN
|
||||

|
||||
|
||||
|
||||
# Commons
|
||||
|
||||
Este proyecto utiliza Java nativo como librería commons
|
||||
|
||||
|
||||
- Banesco Banco Universal © Todos los Derechos Reservados.
|
||||
85
pom.xml
Normal file
85
pom.xml
Normal file
@ -0,0 +1,85 @@
|
||||
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
<groupId>com.banesco</groupId>
|
||||
<artifactId>commons</artifactId>
|
||||
<version>1.0</version>
|
||||
<packaging>jar</packaging>
|
||||
|
||||
<name>commons</name>
|
||||
<url>http://maven.apache.org</url>
|
||||
|
||||
<properties>
|
||||
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
||||
<maven.compiler.source>17</maven.compiler.source>
|
||||
<maven.compiler.target>17</maven.compiler.target>
|
||||
<java.version>17</java.version>
|
||||
<jakarta.jaxb.api.version>4.0.0</jakarta.jaxb.api.version>
|
||||
<jakarta.jaxb.impl.version>4.0.5</jakarta.jaxb.impl.version>
|
||||
</properties>
|
||||
|
||||
<dependencies>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.fasterxml.jackson.core</groupId>
|
||||
<artifactId>jackson-databind</artifactId>
|
||||
<version>2.15.4</version>
|
||||
<scope>compile</scope>
|
||||
</dependency>
|
||||
<!--dependency>
|
||||
<groupId>org.apache.commons</groupId>
|
||||
<artifactId>commons-lang3</artifactId>
|
||||
<version>3.13.0</version>
|
||||
</dependency-->
|
||||
<dependency>
|
||||
<groupId>javax.servlet</groupId>
|
||||
<artifactId>javax.servlet-api</artifactId>
|
||||
<version>4.0.1</version>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
|
||||
<!-- Dependencias de JAXB para JDK 17 (Jakarta EE) -->
|
||||
<dependency>
|
||||
<groupId>jakarta.xml.bind</groupId>
|
||||
<artifactId>jakarta.xml.bind-api</artifactId>
|
||||
<version>${jakarta.jaxb.api.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.glassfish.jaxb</groupId>
|
||||
<artifactId>jaxb-runtime</artifactId>
|
||||
<version>${jakarta.jaxb.impl.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>com.fasterxml.jackson.datatype</groupId>
|
||||
<artifactId>jackson-datatype-jsr310</artifactId>
|
||||
<version>2.17.1</version>
|
||||
</dependency>
|
||||
|
||||
</dependencies>
|
||||
|
||||
<build>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-compiler-plugin</artifactId>
|
||||
<version>3.11.0</version>
|
||||
<configuration>
|
||||
<source>17</source>
|
||||
<target>17</target>
|
||||
<release>17</release>
|
||||
</configuration>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-jar-plugin</artifactId>
|
||||
<version>3.3.0</version>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-resources-plugin</artifactId>
|
||||
<version>3.3.1</version>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
</project>
|
||||
8
src/main/java/com/banesco/Commons.java
Normal file
8
src/main/java/com/banesco/Commons.java
Normal file
@ -0,0 +1,8 @@
|
||||
package com.banesco;
|
||||
|
||||
public class Commons {
|
||||
|
||||
public static void main(String[] args) {
|
||||
System.out.println("Commons...");
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,33 @@
|
||||
package com.banesco.common.application.exception;
|
||||
|
||||
public class BanBackendException extends RuntimeException {
|
||||
|
||||
protected String backendCode;
|
||||
protected String backendDesc;
|
||||
protected String target;
|
||||
|
||||
public BanBackendException(String backendCode, String backendDesc) {
|
||||
super(backendDesc);
|
||||
this.backendCode = backendCode;
|
||||
this.backendDesc = backendDesc;
|
||||
}
|
||||
|
||||
public BanBackendException(String backendCode, String backendDesc, String target) {
|
||||
super(backendDesc.formatted(target) + ", Target:" + target);
|
||||
this.backendCode = backendCode;
|
||||
this.backendDesc = backendDesc;
|
||||
this.target = target;
|
||||
}
|
||||
|
||||
public String getBackendCode() {
|
||||
return backendCode;
|
||||
}
|
||||
|
||||
public String getBackendDesc() {
|
||||
return backendDesc;
|
||||
}
|
||||
|
||||
public String getTarget() {
|
||||
return target;
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,32 @@
|
||||
package com.banesco.common.application.exception;
|
||||
|
||||
import com.banesco.common.domain.interfaces.BaseStatusCodesEnum;
|
||||
|
||||
public class BanRuntimeException extends RuntimeException {
|
||||
|
||||
protected BaseStatusCodesEnum statusCode;
|
||||
protected String target;
|
||||
|
||||
public BanRuntimeException() {
|
||||
super("Internal Error");
|
||||
}
|
||||
|
||||
public BanRuntimeException(BaseStatusCodesEnum statusCode, String target) {
|
||||
super(statusCode.getStatusDesc().formatted(target) + ", Target:" + target);
|
||||
this.statusCode = statusCode;
|
||||
this.target = target;
|
||||
}
|
||||
|
||||
public BanRuntimeException(BaseStatusCodesEnum statusCode) {
|
||||
super(statusCode.getStatusDesc());
|
||||
this.statusCode = statusCode;
|
||||
}
|
||||
|
||||
public BaseStatusCodesEnum getStatusCode() {
|
||||
return statusCode;
|
||||
}
|
||||
|
||||
public String getTarget() {
|
||||
return target;
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,36 @@
|
||||
package com.banesco.common.domain.dto.bian.customer;
|
||||
|
||||
public class CustomerReference {
|
||||
String customerIdType;
|
||||
String customerId;
|
||||
|
||||
public CustomerReference() {
|
||||
}
|
||||
|
||||
public CustomerReference(String customerIdType, String customerId) {
|
||||
this.customerIdType = customerIdType;
|
||||
this.customerId = customerId;
|
||||
}
|
||||
|
||||
public String getCustomerIdType() {
|
||||
return customerIdType;
|
||||
}
|
||||
|
||||
public void setCustomerIdType(String customerIdType) {
|
||||
this.customerIdType = customerIdType;
|
||||
}
|
||||
|
||||
public String getCustomerId() {
|
||||
return customerId;
|
||||
}
|
||||
|
||||
public void setCustomerId(String customerId) {
|
||||
this.customerId = customerId;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "{\"customerIdType\":\"%s\",\"customerId\":\"%s\"}"
|
||||
.formatted(customerIdType, customerId);
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,59 @@
|
||||
package com.banesco.common.domain.dto.bian.device;
|
||||
|
||||
|
||||
|
||||
public class BianDevice {
|
||||
String deviceType;
|
||||
String deviceDescription;
|
||||
String deviceIp;
|
||||
String deviceSessionReference;
|
||||
|
||||
public BianDevice() {
|
||||
|
||||
}
|
||||
|
||||
public BianDevice(String deviceType, String deviceDescription, String deviceIp, String deviceSessionReference) {
|
||||
this.deviceType = deviceType;
|
||||
this.deviceDescription = deviceDescription;
|
||||
this.deviceIp = deviceIp;
|
||||
this.deviceSessionReference = deviceSessionReference;
|
||||
}
|
||||
|
||||
public String getDeviceType() {
|
||||
return deviceType;
|
||||
}
|
||||
|
||||
public void setDeviceType(String deviceType) {
|
||||
this.deviceType = deviceType;
|
||||
}
|
||||
|
||||
public String getDeviceDescription() {
|
||||
return deviceDescription;
|
||||
}
|
||||
|
||||
public void setDeviceDescription(String deviceDescription) {
|
||||
this.deviceDescription = deviceDescription;
|
||||
}
|
||||
|
||||
public String getDeviceIp() {
|
||||
return deviceIp;
|
||||
}
|
||||
|
||||
public void setDeviceIp(String deviceIp) {
|
||||
this.deviceIp = deviceIp;
|
||||
}
|
||||
|
||||
public String getDeviceSessionReference() {
|
||||
return deviceSessionReference;
|
||||
}
|
||||
|
||||
public void setDeviceSessionReference(String deviceSessionReference) {
|
||||
this.deviceSessionReference = deviceSessionReference;
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return "{\"deviceType\":\"%s\",\"deviceDescription\":\"%s\",\"deviceIp\":\"%s\",\"deviceSessionReference\":\"%s\"}"
|
||||
.formatted(deviceType, deviceDescription, deviceIp, deviceSessionReference);
|
||||
}
|
||||
|
||||
}
|
||||
@ -0,0 +1,6 @@
|
||||
package com.banesco.common.domain.dto.bian.paymentCard;
|
||||
|
||||
public enum CardTypeValues {
|
||||
DebitCard,
|
||||
CreditCard
|
||||
}
|
||||
@ -0,0 +1,33 @@
|
||||
package com.banesco.common.domain.dto.bian.response;
|
||||
|
||||
public class BaseResponse<T, K> {
|
||||
protected T statusResponse;
|
||||
|
||||
protected K dataResponse;
|
||||
|
||||
public BaseResponse() {
|
||||
}
|
||||
|
||||
public BaseResponse(T statusResponse, K dataResponse) {
|
||||
|
||||
this.statusResponse = statusResponse;
|
||||
this.dataResponse = dataResponse;
|
||||
|
||||
}
|
||||
|
||||
public T getStatusResponse() {
|
||||
return statusResponse;
|
||||
}
|
||||
|
||||
public void setStatusResponse(T statusResponse) {
|
||||
this.statusResponse = statusResponse;
|
||||
}
|
||||
|
||||
public K getDataResponse() {
|
||||
return dataResponse;
|
||||
}
|
||||
|
||||
public void setDataResponse(K statusResponse) {
|
||||
this.dataResponse = dataResponse;
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,10 @@
|
||||
package com.banesco.common.domain.dto.bian.response;
|
||||
|
||||
public record BianStatusResponse(String status, String statusCode, String message, String traceId) {
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "{\"status\":\"%s\",\"statusCode\":\"%s\",\"message\":\"%s\",\"traceId\":\"%s\"}".formatted(status, statusCode, message, traceId);
|
||||
}
|
||||
|
||||
}
|
||||
@ -0,0 +1,10 @@
|
||||
package com.banesco.common.domain.dto.bian.response;
|
||||
|
||||
public record MetadataResponse(String timestamp, String operationId) {
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "{\"timestamp\":\"%s\",\"operationId\":\"%s\"}".formatted(timestamp, operationId);
|
||||
}
|
||||
|
||||
}
|
||||
@ -0,0 +1,6 @@
|
||||
package com.banesco.common.domain.interfaces;
|
||||
|
||||
public interface BaseStatusCodesEnum {
|
||||
String getStatusCode();
|
||||
String getStatusDesc();
|
||||
}
|
||||
54
src/main/java/com/banesco/common/domain/model/ApiConfig.java
Normal file
54
src/main/java/com/banesco/common/domain/model/ApiConfig.java
Normal file
@ -0,0 +1,54 @@
|
||||
package com.banesco.common.domain.model;
|
||||
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* Clase de configuración para APIs. Almacena la información necesaria para
|
||||
* conectarse a un servicio API externo, incluyendo URL, configuración de
|
||||
* timeout y parámetros adicionales. Diseñada para ser utilizada como objeto de
|
||||
* configuración en clientes de API y servicios de integración.
|
||||
*/
|
||||
public class ApiConfig {
|
||||
|
||||
String url;
|
||||
ApiTimeout timeout;
|
||||
Map<String, String> config;
|
||||
|
||||
public ApiConfig(){
|
||||
|
||||
}
|
||||
|
||||
public ApiConfig(String url,
|
||||
ApiTimeout timeout,
|
||||
Map<String, String> config) {
|
||||
|
||||
this.url = url;
|
||||
this.timeout = timeout;
|
||||
this.config = config;
|
||||
}
|
||||
|
||||
public String getUrl() {
|
||||
return url;
|
||||
}
|
||||
|
||||
public void setUrl(String url) {
|
||||
this.url = url;
|
||||
}
|
||||
|
||||
public ApiTimeout getTimeout() {
|
||||
return timeout;
|
||||
}
|
||||
|
||||
public void setTimeout(ApiTimeout timeout) {
|
||||
this.timeout = timeout;
|
||||
}
|
||||
|
||||
public Map<String, String> getConfig() {
|
||||
return config;
|
||||
}
|
||||
|
||||
public void setConfig(Map<String, String> config) {
|
||||
this.config = config;
|
||||
}
|
||||
|
||||
}
|
||||
@ -0,0 +1,37 @@
|
||||
package com.banesco.common.domain.model;
|
||||
|
||||
/**
|
||||
* Clase interna que representa la configuración de tiempos de espera
|
||||
* (timeout) para conexiones a APIs. Define los tiempos máximos de espera
|
||||
* para establecer la conexión y para recibir una respuesta, especificados
|
||||
* en milisegundos.
|
||||
*/
|
||||
public class ApiTimeout{
|
||||
private int connect;
|
||||
private int response;
|
||||
|
||||
public ApiTimeout() {
|
||||
|
||||
}
|
||||
public ApiTimeout(int connect, int response) {
|
||||
this.connect = connect;
|
||||
this.response = response;
|
||||
}
|
||||
|
||||
public int getConnect() {
|
||||
return connect;
|
||||
}
|
||||
|
||||
public void setConnect(int connect) {
|
||||
this.connect = connect;
|
||||
}
|
||||
|
||||
public int getResponse() {
|
||||
return response;
|
||||
}
|
||||
|
||||
public void setResponse(int response) {
|
||||
this.response = response;
|
||||
}
|
||||
|
||||
}
|
||||
@ -0,0 +1,63 @@
|
||||
package com.banesco.common.domain.model;
|
||||
|
||||
/**
|
||||
* Clase para obtener los codigos y mensajes de salida
|
||||
*/
|
||||
public class BackResponse {
|
||||
|
||||
private String backendCode;
|
||||
private int httpCode;
|
||||
private String statusCode;
|
||||
private String description;
|
||||
|
||||
public BackResponse() {
|
||||
}
|
||||
|
||||
public BackResponse(String backendCode,
|
||||
int httpCode,
|
||||
String statusCode,
|
||||
String description) {
|
||||
this.backendCode = backendCode;
|
||||
this.httpCode = httpCode;
|
||||
this.statusCode = statusCode;
|
||||
this.description = backendCode;
|
||||
}
|
||||
|
||||
public String getBackendCode() {
|
||||
return backendCode;
|
||||
}
|
||||
|
||||
public int getHttpCode() {
|
||||
return httpCode;
|
||||
}
|
||||
|
||||
public String getStatusCode() {
|
||||
return statusCode;
|
||||
}
|
||||
|
||||
public String getDescription() {
|
||||
return description;
|
||||
}
|
||||
|
||||
public void setBackendCode(String backendCode) {
|
||||
this.backendCode = backendCode;
|
||||
}
|
||||
|
||||
public void setHttpCode(int httpCode) {
|
||||
this.httpCode = httpCode;
|
||||
}
|
||||
|
||||
public void setStatusCode(String statusCode) {
|
||||
this.statusCode = statusCode;
|
||||
}
|
||||
|
||||
public void setDescription(String description) {
|
||||
this.description = description;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "{\"backendCode\":\"%s\",\"httpCode\":%d,\"statusCode\":\"%s\",\"description\":\"%s\"}"
|
||||
.formatted(backendCode, httpCode, statusCode, description);
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,36 @@
|
||||
package com.banesco.common.domain.model;
|
||||
|
||||
public class BaseResponse<T> {
|
||||
|
||||
protected StatusResponse statusResponse;
|
||||
protected T dataResponse;
|
||||
|
||||
public BaseResponse() {
|
||||
}
|
||||
|
||||
public BaseResponse(StatusResponse statusResponse) {
|
||||
this.statusResponse = statusResponse;
|
||||
}
|
||||
|
||||
public BaseResponse(StatusResponse statusResponse, T dataResponse) {
|
||||
this.statusResponse = statusResponse;
|
||||
this.dataResponse = dataResponse;
|
||||
}
|
||||
|
||||
public StatusResponse getStatusResponse() {
|
||||
return statusResponse;
|
||||
}
|
||||
|
||||
public void setStatusResponse(StatusResponse statusResponse) {
|
||||
this.statusResponse = statusResponse;
|
||||
}
|
||||
|
||||
public T getDataResponse() {
|
||||
return dataResponse;
|
||||
}
|
||||
|
||||
public void setDataResponse(T dataResponse) {
|
||||
this.dataResponse = dataResponse;
|
||||
}
|
||||
|
||||
}
|
||||
50
src/main/java/com/banesco/common/domain/model/Device.java
Normal file
50
src/main/java/com/banesco/common/domain/model/Device.java
Normal file
@ -0,0 +1,50 @@
|
||||
package com.banesco.common.domain.model;
|
||||
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
public class Device {
|
||||
private String type;
|
||||
private String description;
|
||||
private String ipAddress;
|
||||
|
||||
public Device() {
|
||||
|
||||
}
|
||||
|
||||
public Device(String type, String description, String ipAddress) {
|
||||
this.type = type;
|
||||
this.description = description;
|
||||
this.ipAddress = ipAddress;
|
||||
}
|
||||
|
||||
public String getType() {
|
||||
return type;
|
||||
}
|
||||
|
||||
public String getDescription() {
|
||||
return description;
|
||||
}
|
||||
|
||||
public String getIpAddress() {
|
||||
return ipAddress;
|
||||
}
|
||||
|
||||
public void setType(String type) {
|
||||
this.type = type;
|
||||
}
|
||||
|
||||
public void setDescription(String description) {
|
||||
this.description = description;
|
||||
}
|
||||
|
||||
public void setIpAddress(String ipAddress) {
|
||||
this.ipAddress = ipAddress;
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return "{\"type\":\"%s\",\"ipAddress\":\"%s\",\"description\":\"%s\"}".formatted(type, ipAddress, description);
|
||||
}
|
||||
|
||||
}
|
||||
@ -0,0 +1,31 @@
|
||||
package com.banesco.common.domain.model;
|
||||
|
||||
|
||||
public class RedisParam {
|
||||
private String prefix;
|
||||
private long expiration;
|
||||
|
||||
public RedisParam() {
|
||||
}
|
||||
|
||||
public RedisParam(String prefix, long expiration) {
|
||||
this.prefix = prefix;
|
||||
this.expiration = expiration;
|
||||
}
|
||||
|
||||
public String getPrefix() {
|
||||
return prefix;
|
||||
}
|
||||
|
||||
public void setPrefix(String prefix) {
|
||||
this.prefix = prefix;
|
||||
}
|
||||
|
||||
public long getExpiration() {
|
||||
return expiration;
|
||||
}
|
||||
|
||||
public void setExpiration(long expiration) {
|
||||
this.expiration = expiration;
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,10 @@
|
||||
package com.banesco.common.domain.model;
|
||||
|
||||
public record StatusResponse(String statusCode, String statusDesc) {
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "{\"statusCode\":\"" + statusCode + "\",\"statusDesc\":\"" + statusDesc + "\"}";
|
||||
}
|
||||
|
||||
}
|
||||
@ -0,0 +1,20 @@
|
||||
package com.banesco.common.infraestructure.config;
|
||||
|
||||
public enum DeviceTypeValues {
|
||||
Mobile,
|
||||
Tablet,
|
||||
PersonalComputer,
|
||||
SecureCardReader,
|
||||
NonSecureCardReader,
|
||||
OtherNational,
|
||||
OtherPrivate,
|
||||
Wearable,
|
||||
Vehicle,
|
||||
Embedded,
|
||||
KeyFob,
|
||||
Jewellery,
|
||||
Sticker,
|
||||
GamingDevice,
|
||||
Watch,
|
||||
Unknown
|
||||
}
|
||||
@ -0,0 +1,21 @@
|
||||
package com.banesco.common.infraestructure.helpers;
|
||||
|
||||
|
||||
/**
|
||||
* Clase utilitaria para operaciones relacionadas con cuentas bancarias.
|
||||
* Proporciona métodos para manipular y formatear información de cuentas.
|
||||
*/
|
||||
public class AccountHelper {
|
||||
|
||||
/**
|
||||
* Enmascara un número de cuenta, mostrando solo los primeros 4
|
||||
* y últimos 4 Los dígitos intermedios son reemplazados por asteriscos para proteger la
|
||||
* información sensible del cliente.
|
||||
*
|
||||
* @param clearAccountId El número de cuenta completo sin enmascarar
|
||||
* @return El número de cuenta enmascarado en formato "XXXX************YYYY"
|
||||
*/
|
||||
public static String getMaskedAccountId(String clearAccountId) {
|
||||
return clearAccountId.substring(0, 4) + "************" + clearAccountId.substring(clearAccountId.length() - 4);
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,112 @@
|
||||
package com.banesco.common.infraestructure.helpers;
|
||||
|
||||
import java.time.ZoneId;
|
||||
import java.time.ZonedDateTime;
|
||||
import java.time.format.DateTimeFormatter;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* Clase de utilidad para operaciones comunes de fecha y hora.
|
||||
* Utiliza el API moderno de Java (java.time).
|
||||
*/
|
||||
public final class DateHelper {
|
||||
|
||||
// Define la zona horaria de Venezuela una sola vez.
|
||||
private static final ZoneId VENEZUELA_ZONE_ID = ZoneId.of("America/Caracas");
|
||||
|
||||
// Define los formatos de fecha y hora como constantes para reutilizarlos.
|
||||
private static final DateTimeFormatter DATE_FORMATTER = DateTimeFormatter.ofPattern("yyyy-MM-dd");
|
||||
private static final DateTimeFormatter TIME_FORMATTER = DateTimeFormatter.ofPattern("HH:mm:ss");
|
||||
|
||||
// Instancia única para el patrón Singleton (compatibilidad con código existente)
|
||||
private static final DateHelper INSTANCE = new DateHelper();
|
||||
|
||||
/**
|
||||
* Constructor privado para prevenir que la clase sea instanciada directamente.
|
||||
*/
|
||||
private DateHelper() {
|
||||
// Clase de utilidad, no necesita ser instanciada.
|
||||
}
|
||||
|
||||
/**
|
||||
* Obtiene la instancia única de DateHelper (patrón Singleton).
|
||||
* @return La instancia única de DateHelper.
|
||||
*/
|
||||
public static DateHelper getInstance() {
|
||||
return INSTANCE;
|
||||
}
|
||||
|
||||
/**
|
||||
* Obtiene la fecha y/o hora actual en la zona horaria de Venezuela.
|
||||
*
|
||||
* @param separate Un flag que indica si se deben devolver la fecha y la hora por separado.
|
||||
* - Si es `false`, devuelve una sola cadena "yyyy-MM-dd HH:mm:ss".
|
||||
* - Si es `true`, devuelve un Map con las llaves "date" y "time".
|
||||
* @return Un objeto (String o Map) con la fecha y hora formateadas.
|
||||
*/
|
||||
public static Object getCurrentVenezuelanDateTime(boolean separate) {
|
||||
// Obtiene la fecha y hora actual en la zona horaria especificada.
|
||||
ZonedDateTime now = ZonedDateTime.now(VENEZUELA_ZONE_ID);
|
||||
|
||||
if (separate) {
|
||||
// Devuelve las partes en un mapa
|
||||
Map<String, String> dateTimeParts = new HashMap<>();
|
||||
dateTimeParts.put("date", now.format(DATE_FORMATTER));
|
||||
dateTimeParts.put("time", now.format(TIME_FORMATTER));
|
||||
return dateTimeParts;
|
||||
} else {
|
||||
// Devuelve una sola cadena de texto combinada
|
||||
return now.format(DATE_FORMATTER) + " " + now.format(TIME_FORMATTER);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Función de conveniencia para obtener solo la fecha actual formateada.
|
||||
* @return La fecha actual como un String "yyyy-MM-dd".
|
||||
*/
|
||||
public static String getCurrentVenezuelanDate() {
|
||||
return ZonedDateTime.now(VENEZUELA_ZONE_ID).format(DATE_FORMATTER);
|
||||
}
|
||||
|
||||
/**
|
||||
* Función de conveniencia para obtener solo la hora actual formateada.
|
||||
* @return La hora actual como un String "HH:mm:ss".
|
||||
*/
|
||||
public static String getCurrentVenezuelanTime() {
|
||||
return ZonedDateTime.now(VENEZUELA_ZONE_ID).format(TIME_FORMATTER);
|
||||
}
|
||||
|
||||
/**
|
||||
* Verifica si una hora está dentro de un rango especificado.
|
||||
*
|
||||
* @param hourBegin Hora de inicio en formato HHmm (ej: 800 para 08:00, 1800 para 18:00).
|
||||
* @param hourFinish Hora de fin en formato HHmm (ej: 800 para 08:00, 1800 para 18:00).
|
||||
* @param timeString Hora a verificar en formato "HH:mm:ss" o "HH:mm".
|
||||
* @return true si la hora está dentro del rango [hourBegin, hourFinish], false en caso contrario.
|
||||
*/
|
||||
public boolean isHourInRange(int hourBegin, int hourFinish, String timeString) {
|
||||
if (timeString == null || timeString.trim().isEmpty()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Extrae las horas y minutos del String (formato "HH:mm:ss" o "HH:mm")
|
||||
String[] timeParts = timeString.split(":");
|
||||
if (timeParts.length < 2) {
|
||||
return false;
|
||||
}
|
||||
|
||||
try {
|
||||
int hour = Integer.parseInt(timeParts[0]);
|
||||
int minute = Integer.parseInt(timeParts[1]);
|
||||
|
||||
// Convierte la hora a formato HHmm
|
||||
int currentHour = hour * 100 + minute;
|
||||
|
||||
// Verifica si está en el rango
|
||||
return currentHour >= hourBegin && currentHour <= hourFinish;
|
||||
} catch (NumberFormatException e) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,154 @@
|
||||
package com.banesco.common.infraestructure.helpers;
|
||||
|
||||
import com.banesco.common.domain.dto.bian.device.BianDevice;
|
||||
import com.banesco.common.domain.model.Device;
|
||||
import com.banesco.common.infraestructure.config.DeviceTypeValues;
|
||||
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import java.util.Objects;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
import java.util.stream.Collectors;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
public class DeviceHelper {
|
||||
|
||||
private boolean readDeviceFromRequest;
|
||||
private final String DESKTOP = "Desktop";
|
||||
private static final Logger logger = Logger.getLogger(DeviceHelper.class.getName());
|
||||
/**
|
||||
* Nombres de cabeceras HTTP que pueden contener la dirección IP del
|
||||
* cliente. Se revisan en orden para encontrar la IP real considerando
|
||||
* proxies y balanceadores.
|
||||
*/
|
||||
private final String[] IP_HEADER_NAMES = {
|
||||
"X-Forwarded-For",
|
||||
"Proxy-Client-IP",
|
||||
"WL-Proxy-Client-IP",
|
||||
"HTTP_X_FORWARDED_FOR",
|
||||
"HTTP_X_FORWARDED",
|
||||
"HTTP_X_CLUSTER_CLIENT_IP",
|
||||
"HTTP_CLIENT_IP",
|
||||
"HTTP_FORWARDED_FOR",
|
||||
"HTTP_FORWARDED",
|
||||
"HTTP_VIA",
|
||||
"REMOTE_ADDR"
|
||||
};
|
||||
|
||||
public DeviceHelper() {
|
||||
// Lee la propiedad del sistema. Si no existe, asume false por defecto.
|
||||
String readDeviceProperty = System.getProperty("api.server-request.read-device");
|
||||
this.readDeviceFromRequest = readDeviceProperty == null ? false : Boolean.parseBoolean(readDeviceProperty);
|
||||
}
|
||||
|
||||
/**
|
||||
* Obtiene la dirección IP remota del cliente a partir de la solicitud HTTP.
|
||||
* Revisa varias cabeceras HTTP que podrían contener la IP real del cliente
|
||||
* considerando proxies y balanceadores de carga.
|
||||
*
|
||||
* @param request La solicitud HTTP
|
||||
* @return La dirección IP remota del cliente, o "0.0.0.0" si la solicitud
|
||||
* es nula
|
||||
*/
|
||||
public String getRemoteIP(HttpServletRequest request) {
|
||||
if (request == null) {
|
||||
return "0.0.0.0";
|
||||
}
|
||||
|
||||
for (String header : IP_HEADER_NAMES) {
|
||||
String ipList = request.getHeader(header);
|
||||
if (!StringHelper.isEmpty(ipList) && !"unknown".equalsIgnoreCase(ipList)) {
|
||||
return ipList.split(",")[0];
|
||||
}
|
||||
}
|
||||
|
||||
return request.getRemoteAddr();
|
||||
}
|
||||
|
||||
/**
|
||||
* Llena la información del dispositivo remoto del cliente en el objeto
|
||||
* Device. Si se configura readDeviceFromRequest como true, siempre se
|
||||
* obtendrá la información del dispositivo desde la solicitud HTTP,
|
||||
* independientemente de si ya existe.
|
||||
*
|
||||
* @param servletRequest La solicitud HTTP
|
||||
* @param device El objeto Device existente a actualizar o null para crear
|
||||
* uno nuevo
|
||||
* @return El objeto Device con la información del cliente actualizada
|
||||
*/
|
||||
public Device fillRemoteDevice(HttpServletRequest servletRequest, Device device) {
|
||||
if (device == null) {
|
||||
device = new Device();
|
||||
}
|
||||
if (StringHelper.isEmpty(device.getIpAddress()) || readDeviceFromRequest) {
|
||||
device.setIpAddress(getRemoteIP(servletRequest));
|
||||
String userAgent = servletRequest.getHeader("user-agent");
|
||||
if (userAgent == null) {
|
||||
|
||||
device.setType(DESKTOP);
|
||||
device.setDescription(DESKTOP);
|
||||
} else {
|
||||
device.setDescription(userAgent);
|
||||
if (userAgent.toLowerCase().contains("mobi")) {
|
||||
device.setType("Mobile");
|
||||
} else {
|
||||
device.setType(DESKTOP);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return device;
|
||||
}
|
||||
|
||||
/**
|
||||
* Mapea el tipo de dispositivo desde el objeto BianDevice al enum DeviceTypeValues.
|
||||
*
|
||||
* @param device
|
||||
* @return
|
||||
*/
|
||||
public static DeviceTypeValues getDeviceTypeValue(
|
||||
BianDevice device
|
||||
) {
|
||||
var deviceTypeValue = DeviceTypeValues.Unknown;
|
||||
|
||||
if (!Objects.isNull(device) && !StringHelper.isEmpty(device.getDeviceType())) {
|
||||
try {
|
||||
deviceTypeValue = DeviceTypeValues.valueOf(device.getDeviceType());
|
||||
} catch (Exception e) {
|
||||
logger.log(Level.WARNING, "Error Mapping Device Type: %s -> %s".formatted(device.getDeviceType(), e.getMessage()));
|
||||
}
|
||||
}
|
||||
|
||||
return deviceTypeValue;
|
||||
}
|
||||
|
||||
/**
|
||||
* Valida si el tipo de dispositivo es válido según el enum DeviceTypeValues.
|
||||
*
|
||||
* @param type
|
||||
* @return
|
||||
*/
|
||||
public static boolean isValidDeviceType(String type) {
|
||||
|
||||
for (DeviceTypeValues deviceType : DeviceTypeValues.values()) {
|
||||
if (deviceType.name().equals(type)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Obtiene una cadena con todos los tipos de dispositivos válidos.
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
public static String getDeviceTypes() {
|
||||
return Stream.of(DeviceTypeValues.values()).map(Enum::name).collect(
|
||||
Collectors.joining(", ")
|
||||
);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@ -0,0 +1,127 @@
|
||||
package com.banesco.common.infraestructure.helpers;
|
||||
|
||||
import com.fasterxml.jackson.core.JsonProcessingException;
|
||||
import com.fasterxml.jackson.databind.DeserializationFeature;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import com.fasterxml.jackson.databind.SerializationFeature;
|
||||
import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
|
||||
public class JsonHelper {
|
||||
|
||||
private static final Logger logger = Logger.getLogger(JsonHelper.class.getName());
|
||||
public static final ObjectMapper MAPPER = new ObjectMapper();
|
||||
|
||||
static {
|
||||
MAPPER.configure(SerializationFeature.FAIL_ON_EMPTY_BEANS, false);
|
||||
MAPPER.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false);
|
||||
MAPPER.disable(SerializationFeature.WRITE_DATES_AS_TIMESTAMPS);
|
||||
|
||||
// Intentar registrar módulos automáticamente (incluye JavaTimeModule si está disponible)
|
||||
try {
|
||||
MAPPER.findAndRegisterModules();
|
||||
} catch (Exception e) {
|
||||
logger.log(Level.WARNING, "Error auto-registering Jackson modules, trying manual registration: {0}", e.getMessage());
|
||||
// Fallback: intentar registro manual del JavaTimeModule
|
||||
try {
|
||||
MAPPER.registerModule(new JavaTimeModule());
|
||||
} catch (Exception e2) {
|
||||
logger.log(Level.SEVERE, "Error registering JavaTimeModule: {0}", e2.getMessage());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert Object to jsonString
|
||||
*
|
||||
* @param object El objeto a convertir en JSON.
|
||||
* @return La cadena JSON resultante o null si ocurre un error.
|
||||
*/
|
||||
public static String getJsonFromObject(Object object) {
|
||||
if (object == null) {
|
||||
return "null";
|
||||
}
|
||||
try {
|
||||
return MAPPER.writeValueAsString(object);
|
||||
} catch (JsonProcessingException e) {
|
||||
logger.log(Level.SEVERE, "Error parsing objeto a JSON: {0}", e.getMessage());
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert Object to jsonString in compact format (single line, includes nulls)
|
||||
*
|
||||
* @param object El objeto a convertir en JSON.
|
||||
* @return La cadena JSON compacta en una sola línea o null si ocurre un error.
|
||||
*/
|
||||
public static String getJsonFromObjectExcludingNulls(Object object) {
|
||||
if (object == null) {
|
||||
return "null";
|
||||
}
|
||||
try {
|
||||
// Usar el formato compacto (sin pretty print) pero manteniendo todos los campos incluyendo nulls
|
||||
return MAPPER.writeValueAsString(object);
|
||||
} catch (JsonProcessingException e) {
|
||||
logger.log(Level.SEVERE, "Error parsing objeto a JSON: {0}", e.getMessage());
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Convierte una cadena JSON en un objeto Java de la clase especificada.
|
||||
*
|
||||
* @param json La cadena JSON a convertir.
|
||||
* @param className La clase del objeto Java resultante.
|
||||
* @param <T> El tipo del objeto resultante.
|
||||
* @return El objeto Java resultante, o null si ocurre un error o la cadena
|
||||
* JSON está vacía.
|
||||
*/
|
||||
public static <T> T getObjectFromJson(String json, Class<T> className) {
|
||||
if (json == null || json.isEmpty()) {
|
||||
return null;
|
||||
}
|
||||
try {
|
||||
return MAPPER.readValue(json, className);
|
||||
} catch (JsonProcessingException | IllegalArgumentException e) {
|
||||
logger.log(Level.WARNING, "Error parsing JSON a objeto: {0}", e.getMessage());
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
public static <T> List<T> getListFromJson(String json, Class<T> className) {
|
||||
if (json == null || json.isEmpty()) {
|
||||
return new ArrayList<>();
|
||||
}
|
||||
try {
|
||||
return MAPPER.readValue(json,
|
||||
MAPPER.getTypeFactory().constructCollectionType(List.class, className)
|
||||
);
|
||||
} catch (JsonProcessingException | IllegalArgumentException e) {
|
||||
logger.log(Level.WARNING, "Error parsing JSON a List Object: {0}", e.getMessage());
|
||||
}
|
||||
|
||||
return new ArrayList<>();
|
||||
}
|
||||
|
||||
public static <T> List<T> getListFromInputStream(InputStream inputStream, Class<T> className) throws IOException {
|
||||
if (inputStream == null) {
|
||||
return new ArrayList<>();
|
||||
}
|
||||
try {
|
||||
return MAPPER.readValue(inputStream,
|
||||
MAPPER.getTypeFactory().constructCollectionType(List.class, className)
|
||||
);
|
||||
} catch (JsonProcessingException | IllegalArgumentException e) {
|
||||
logger.log(Level.WARNING, "Error parsing JSON a List Object: {0}", e.getMessage());
|
||||
}
|
||||
|
||||
return new ArrayList<>();
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,160 @@
|
||||
package com.banesco.common.infraestructure.helpers;
|
||||
|
||||
import java.util.Map;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
/**
|
||||
* Clase utilitaria para la generación de mensajes de registro (logging).
|
||||
* Facilita la creación de cadenas formateadas para registrar información de
|
||||
* solicitudes y respuestas, tanto públicas como privadas, así como mensajes de
|
||||
* error. Utiliza un formato estandarizado para mejorar la legibilidad y
|
||||
* facilitar el análisis de los registros del sistema.
|
||||
*/
|
||||
public class LoggerHelper {
|
||||
|
||||
/**
|
||||
* Formatea un mapa de headers en un String con un header por línea.
|
||||
* Ejemplo: "Header1: valor1\nHeader2: valor2"
|
||||
*
|
||||
* @param headers El mapa de headers a formatear.
|
||||
* @return Un String formateado y listo para ser logueado.
|
||||
*/
|
||||
public static String formatHeaders(Map<String, String> headers) {
|
||||
if(headers == null) {
|
||||
return "Headers: [vacios]";
|
||||
}
|
||||
|
||||
return headers.entrySet().stream()
|
||||
.map(entry -> entry.getKey() + ": " + entry.getValue())
|
||||
.collect(Collectors.joining("\n", "\n Headers: \n", ""));
|
||||
}
|
||||
|
||||
/**
|
||||
* Construye una cadena de información para una solicitud pública.
|
||||
*
|
||||
* @param requestId El ID de la solicitud.
|
||||
* @param request El objeto de solicitud.
|
||||
* @param <T> El tipo del objeto de solicitud.
|
||||
* @return Una cadena de información formateada.
|
||||
*/
|
||||
public static <T> String buildInfoRequest(String requestId, T request) {
|
||||
return String.format("[PUB RQ: %s] %s", requestId, JsonHelper.getJsonFromObject(request));
|
||||
}
|
||||
|
||||
/**
|
||||
* Construye una cadena de información para una solicitud pública.
|
||||
*
|
||||
* @param requestId El ID de la solicitud.
|
||||
* @param request El request en cadena de la solicitud.
|
||||
* @return Una cadena de información formateada.
|
||||
*/
|
||||
public static <T> String buildInfoRequest(String requestId, String request) {
|
||||
return String.format("[PUB RQ: %s] %s", requestId, request);
|
||||
}
|
||||
|
||||
/**
|
||||
* Construye una cadena de información para una respuesta pública.
|
||||
*
|
||||
* @param requestId El ID de la solicitud.
|
||||
* @param response El objeto de respuesta.
|
||||
* @param <T> El tipo del objeto de respuesta.
|
||||
* @return Una cadena de información formateada.
|
||||
*/
|
||||
public static <T> String buildInfoResponse(String requestId, T response) {
|
||||
return String.format("[PUB RS: %s] %s", requestId, JsonHelper.getJsonFromObject(response));
|
||||
}
|
||||
|
||||
/**
|
||||
* Construye una cadena de información para una respuesta pública.
|
||||
*
|
||||
* @param requestId El ID de la solicitud.
|
||||
* @param response El objeto en cadena de respuesta.
|
||||
* @return Una cadena de información formateada.
|
||||
*/
|
||||
public static String buildInfoResponse(String requestId, String response) {
|
||||
return String.format("[PUB RS: %s] %s", requestId, response);
|
||||
}
|
||||
|
||||
/**
|
||||
* Construye una cadena de información para una solicitud privada.
|
||||
*
|
||||
* @param requestId El ID de la solicitud.
|
||||
* @param name El nombre de la solicitud privada.
|
||||
* @param request El objeto de solicitud.
|
||||
* @param <T> El tipo del objeto de solicitud.
|
||||
* @return Una cadena de información formateada.
|
||||
*/
|
||||
public static <T> String buildInfoPrivateRequest(String requestId, String name, T request) {
|
||||
return String.format("[PRV RQ %s: %s] %s", requestId, name, JsonHelper.getJsonFromObject(request));
|
||||
}
|
||||
|
||||
/**
|
||||
* Construye una cadena de información para una solicitud privada.
|
||||
*
|
||||
* @param requestId El ID de la solicitud.
|
||||
* @param request El objeto de solicitud.
|
||||
* @return Una cadena de información formateada.
|
||||
*/
|
||||
public static String buildInfoPrivateRequest(String requestId, String request) {
|
||||
return String.format("[PRV RQ: %s] %s", requestId, request);
|
||||
}
|
||||
|
||||
/**
|
||||
* Construye una cadena de información para una solicitud privada.
|
||||
*
|
||||
* @param requestId El ID de la solicitud.
|
||||
* @param name El nombre de la solicitud privada.
|
||||
* @param request El objeto en cadena de la solicitud.
|
||||
* @return Una cadena de información formateada.
|
||||
*/
|
||||
public static String buildInfoPrivateRequest(String requestId, String name, String request) {
|
||||
return String.format("[PRV RQ %s: %s] %s", requestId, name, request);
|
||||
}
|
||||
|
||||
/**
|
||||
* Construye una cadena de información para una respuesta privada.
|
||||
*
|
||||
* @param requestId El ID de la solicitud.
|
||||
* @param name El nombre de la respuesta privada.
|
||||
* @param response El objeto de respuesta.
|
||||
* @param <T> El tipo del objeto de respuesta.
|
||||
* @return Una cadena de información formateada.
|
||||
*/
|
||||
public static <T> String buildInfoPrivateResponse(String requestId, String name, T response) {
|
||||
return String.format("[PRV RS %s: %s] %s", requestId, name, JsonHelper.getJsonFromObject(response));
|
||||
}
|
||||
|
||||
/**
|
||||
* Construye una cadena de información para una respuesta privada.
|
||||
*
|
||||
* @param requestId El ID de la solicitud.
|
||||
* @param response El objeto en cadena de la respuesta.
|
||||
* @return Una cadena de información formateada.
|
||||
*/
|
||||
public static String buildInfoPrivateResponse(String requestId, String response) {
|
||||
return String.format("[PRV RS: %s] %s", requestId, response);
|
||||
}
|
||||
|
||||
/**
|
||||
* Construye una cadena de información para una respuesta privada.
|
||||
*
|
||||
* @param requestId El ID de la solicitud.
|
||||
* @param name El nombre de la respuesta privada.
|
||||
* @param response El objeto en cadena de la respuesta.
|
||||
* @return Una cadena de información formateada.
|
||||
*/
|
||||
public static String buildInfoPrivateResponse(String requestId, String name, String response) {
|
||||
return String.format("[PRV RS %s: %s] %s", requestId, name, response);
|
||||
}
|
||||
|
||||
/**
|
||||
* Construye una cadena de error.
|
||||
*
|
||||
* @param requestId El ID de la solicitud asociada al error.
|
||||
* @param out El mensaje de error.
|
||||
* @return Una cadena de error formateada.
|
||||
*/
|
||||
public static String buildError(String requestId, String out) {
|
||||
return String.format("[ERROR %s] %s", requestId, out);
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,15 @@
|
||||
package com.banesco.common.infraestructure.helpers;
|
||||
|
||||
import com.banesco.common.domain.dto.bian.paymentCard.CardTypeValues;
|
||||
|
||||
public class PaymentCardHelper {
|
||||
|
||||
public static boolean isValidCardType(String type) {
|
||||
for (CardTypeValues cardTypeValue : CardTypeValues.values()) {
|
||||
if (cardTypeValue.name().equals(type)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,81 @@
|
||||
package com.banesco.common.infraestructure.helpers;
|
||||
|
||||
import java.util.concurrent.ThreadLocalRandom;
|
||||
|
||||
/**
|
||||
* Clase utilitaria para operaciones relacionadas con solicitudes HTTP y
|
||||
* generación de identificadores. Proporciona métodos para generar IDs únicos,
|
||||
* obtener información del cliente y gestionar información del dispositivo.
|
||||
*/
|
||||
public class RequestHelper {
|
||||
|
||||
private final static String ALPHANUMERIC_CHARACTERS = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";
|
||||
private final static int baseCharacterLen = ALPHANUMERIC_CHARACTERS.length();
|
||||
|
||||
|
||||
/**
|
||||
* Permite tener una cadena aleatoria de caracteres numericos
|
||||
*
|
||||
* @param len longitud de la cadena numerica a retornar
|
||||
* @return
|
||||
*/
|
||||
public String randomNumeric(int len) {
|
||||
char[] chars = new char[len];
|
||||
for (int i = 0; i < len; i++) {
|
||||
chars[i] = (char) ThreadLocalRandom.current().nextInt(48, 58); // ascii index number
|
||||
}
|
||||
|
||||
return new String(chars);
|
||||
}
|
||||
|
||||
/**
|
||||
* Permite tener una cadena aleatoria de caracteres alfa-numericos
|
||||
*
|
||||
* @param len longitud de la cadena alfa-numerica a retornar
|
||||
* @return
|
||||
*/
|
||||
public static String randomAlphanumeric(int len) {
|
||||
char[] chars = new char[len];
|
||||
for (int i = 0; i < len; i++) {
|
||||
chars[i] = ALPHANUMERIC_CHARACTERS.charAt(ThreadLocalRandom.current().nextInt(baseCharacterLen));
|
||||
}
|
||||
|
||||
return new String(chars);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Retorna Identificador de la Instancia del Request, usando como prefijo un valor predefinido
|
||||
* ejemplos: P2P, REM,
|
||||
* Facilita identificar el origen de los Requests
|
||||
* Deberia obtenerse una vez al inicia el Request
|
||||
*
|
||||
* @param apiSourceId
|
||||
* @return
|
||||
*/
|
||||
public String getInstanceId(String apiSourceId) {
|
||||
return (apiSourceId == null ? "INST" : apiSourceId).concat(randomAlphanumeric(10));
|
||||
}
|
||||
|
||||
/**
|
||||
* Retorna un Identificador del Request, se sugiere usar el getInstanceId creada como prefijo.
|
||||
* Usar uno para Cada Request que implique afectacion financiera
|
||||
*
|
||||
* @param instanceId
|
||||
* @return
|
||||
*/
|
||||
public static String getRequestId(String instanceId) {
|
||||
return instanceId.concat("REQ").concat(randomAlphanumeric(20));
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Permite Obtener un valor Numerico de Identificador de Transaccion
|
||||
*
|
||||
* @param len
|
||||
* @return
|
||||
*/
|
||||
public String getTransactionId(int len) {
|
||||
return randomNumeric(len);
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,106 @@
|
||||
package com.banesco.common.infraestructure.helpers;
|
||||
|
||||
/**
|
||||
* Clase utilitaria para operaciones con cadenas de texto (strings). Proporciona
|
||||
* métodos para validar, manipular y formatear cadenas de texto. Incluye
|
||||
* funcionalidades como verificación de tipos numéricos, validación de cadenas
|
||||
* no vacías y funciones de formato como relleno de caracteres.
|
||||
*/
|
||||
public class StringHelper {
|
||||
|
||||
/**
|
||||
* Verifica si una cadena de texto representa un número entero.
|
||||
*
|
||||
* @param value La cadena de texto a verificar.
|
||||
* @return true si la cadena es un número entero válido, false en caso
|
||||
* contrario.
|
||||
* @throws NumberFormatException Si el string no tiene el formato adeacuado
|
||||
*/
|
||||
public static boolean isNumeric(String value) {
|
||||
if (value == null || value.isEmpty()) {
|
||||
return false;
|
||||
}
|
||||
try {
|
||||
Integer.parseInt(value);
|
||||
return true;
|
||||
} catch (NumberFormatException e) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Verifica si una cadena de texto es nula o está vacía después de
|
||||
* eliminar espacios en blanco.
|
||||
*
|
||||
* @param value La cadena de texto a verificar.
|
||||
* @return true si la cadena está vacía, false en caso contrario.
|
||||
*/
|
||||
public static boolean isEmpty(String value) {
|
||||
return value == null || value.trim().isEmpty();
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Rellena una cadena de texto con un carácter específico a la izquierda
|
||||
* hasta alcanzar la longitud deseada.
|
||||
*
|
||||
* @param inputStr La cadena de texto a rellenar.
|
||||
* @param strLenOut La longitud deseada de la cadena resultante.
|
||||
* @param padChar El carácter de relleno.
|
||||
* @return La cadena rellenada con el carácter especificado a la izquierda.
|
||||
*/
|
||||
public static String leftPad(String inputStr, int strLenOut, char padChar) {
|
||||
if (inputStr == null) {
|
||||
inputStr = ""; // Handle null input
|
||||
}
|
||||
int padLength = strLenOut - inputStr.length();
|
||||
if (padLength <= 0) {
|
||||
return inputStr; // No padding needed
|
||||
}
|
||||
|
||||
char[] paddedString = new char[padLength];
|
||||
for (int i = 0; i < padLength; i++) {
|
||||
paddedString[i] = padChar;
|
||||
}
|
||||
|
||||
return new String(paddedString).concat(inputStr);
|
||||
}
|
||||
|
||||
/**
|
||||
* Permite convertir nombre de propiedad separada con (,-) to CamelCase
|
||||
*
|
||||
* @param inputStr Cadena de texto a convertir
|
||||
* @param firstUpper Flag que indica si la primera letra es Mayuscula
|
||||
* @return
|
||||
*/
|
||||
public static String convertToCamelCase(String inputStr, boolean firstUpper) {
|
||||
|
||||
StringBuilder result = new StringBuilder();
|
||||
boolean capitalizeNext = firstUpper;
|
||||
|
||||
for (char ch : inputStr.toCharArray()) {
|
||||
if (ch == '.' || ch == '-') {
|
||||
capitalizeNext = true; // Next character should be capitalized
|
||||
} else {
|
||||
if (capitalizeNext) {
|
||||
result.append(Character.toUpperCase(ch)); // Capitalize current character
|
||||
capitalizeNext = false; // Reset flag
|
||||
} else {
|
||||
result.append(Character.toLowerCase(ch)); // Append in lowercase
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return result.toString();
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @param inputStr Cadena de texto a convertir en UpperCamelCase
|
||||
* @return
|
||||
*/
|
||||
public static String convertToUpperCamelCase(String inputStr) {
|
||||
return convertToCamelCase(inputStr, true);
|
||||
}
|
||||
|
||||
}
|
||||
@ -0,0 +1,168 @@
|
||||
package com.banesco.common.infraestructure.helpers;
|
||||
|
||||
import jakarta.xml.bind.JAXBContext;
|
||||
import jakarta.xml.bind.JAXBElement;
|
||||
import jakarta.xml.bind.JAXBException;
|
||||
import jakarta.xml.bind.Marshaller;
|
||||
|
||||
import javax.xml.namespace.QName;
|
||||
import java.io.ByteArrayOutputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.StringWriter;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
import java.util.Objects;
|
||||
import java.util.concurrent.ConcurrentHashMap;
|
||||
import java.util.concurrent.ConcurrentMap;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
|
||||
/**
|
||||
* Clase de utilidad para trabajar con XML utilizando JAXB.
|
||||
*/
|
||||
public class XmlHelper {
|
||||
private static final Logger logger = Logger.getLogger(XmlHelper.class.getName());
|
||||
|
||||
// Cache para las instancias de JAXBContext.
|
||||
// La creación de JAXBContext es una operación costosa, por lo que cachearlas
|
||||
// mejora significativamente el rendimiento en aplicaciones que procesan XML frecuentemente.
|
||||
// Se utiliza ConcurrentHashMap para garantizar la seguridad en entornos con múltiples hilos (thread-safe).
|
||||
private static final ConcurrentMap<Class<?>, JAXBContext> JAXB_CONTEXT_CACHE = new ConcurrentHashMap<>();
|
||||
|
||||
/**
|
||||
* Constructor privado para evitar la instanciación de esta clase de utilidad.
|
||||
*/
|
||||
private XmlHelper() {
|
||||
throw new UnsupportedOperationException("Esta es una clase de utilidad y no puede ser instanciada.");
|
||||
}
|
||||
|
||||
/**
|
||||
* Imprime el contenido XML de un objeto JAXBElement en el log.
|
||||
* Utiliza JAXB para serializar el objeto a XML y lo formatea para una mejor legibilidad.
|
||||
*
|
||||
* @param element El JAXBElement que contiene el objeto a serializar a XML.
|
||||
* @param traceId requestID.
|
||||
* @throws JAXBException Si ocurre un error durante la serialización JAXB.
|
||||
*/
|
||||
public static void printXml(JAXBElement<?> element, String traceId) throws JAXBException {
|
||||
// Verifica si el elemento es nulo para evitar NullPointerException
|
||||
Objects.requireNonNull(element, "El JAXBElement no puede ser nulo.");
|
||||
|
||||
// Obtiene el tipo declarado del elemento para crear el contexto JAXB.
|
||||
// Esto asegura que JAXB conozca la clase raíz del objeto que se va a serializar.
|
||||
Class<?> declaredType = element.getDeclaredType();
|
||||
|
||||
// Crea una instancia de JAXBContext para el tipo declarado.
|
||||
// JAXBContext es costoso de crear, en aplicaciones de alto rendimiento
|
||||
// se suele cachear o reutilizar. Para este caso de log, es aceptable crearlo aquí.
|
||||
JAXBContext ctx = JAXBContext.newInstance(declaredType);
|
||||
|
||||
// Crea un Marshaller, que es responsable de convertir objetos Java a XML.
|
||||
Marshaller marshaller = ctx.createMarshaller();
|
||||
|
||||
// Configura la propiedad para que el XML de salida esté formateado (indentado).
|
||||
// Esto hace que el XML sea mucho más legible en los logs.
|
||||
marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE);
|
||||
|
||||
// Configura la propiedad para que el XML no incluya la declaración XML (<?xml version="1.0" encoding="UTF-8" standalone="yes"?>).
|
||||
// Esto puede ser útil si solo quieres el contenido XML puro en el log,
|
||||
// pero a menudo es mejor dejarlo si quieres un XML completo y válido.
|
||||
// marshaller.setProperty(Marshaller.JAXB_FRAGMENT, Boolean.TRUE);
|
||||
|
||||
// Usa ByteArrayOutputStream para capturar la salida XML en memoria.
|
||||
// Esto es necesario porque Marshaller escribe en un OutputStream,
|
||||
// y necesitamos obtener el String resultante para el log.
|
||||
try (ByteArrayOutputStream outputStream = new ByteArrayOutputStream()) {
|
||||
// Realiza la serialización del JAXBElement al OutputStream.
|
||||
marshaller.marshal(element, outputStream);
|
||||
|
||||
// Convierte el contenido del ByteArrayOutputStream a un String.
|
||||
// Es crucial especificar la codificación (UTF-8 es lo más común)
|
||||
// para asegurar que los caracteres se interpreten correctamente.
|
||||
String xmlString = outputStream.toString(StandardCharsets.UTF_8.name());
|
||||
|
||||
// Loggea el XML generado.
|
||||
logger.log(Level.INFO, traceId + " - XML del servicio SOAP:\n{0}", xmlString);
|
||||
} catch (IOException e) {
|
||||
// Manejo de excepción si hay un problema con el ByteArrayOutputStream (poco probable en este caso).
|
||||
logger.log(Level.SEVERE, "Error al procesar el OutputStream para el XML", e);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Crea un JAXBElement y lo convierte a un String XML en un solo paso.
|
||||
* <p>
|
||||
* Este es un método de conveniencia de alto nivel que simplifica la generación de XML
|
||||
* al encargarse de la creación del QName y del JAXBElement internamente.
|
||||
*
|
||||
* @param namespaceUri El URI del namespace para el elemento raíz XML.
|
||||
* @param localPart El nombre local del elemento raíz XML (ej: "readCustomerProducts_Rq").
|
||||
* @param declaredType El .class del objeto JAXB que se está serializando.
|
||||
* @param value El objeto de datos JAXB (payload) que se va a convertir.
|
||||
* @param <T> El tipo del objeto de datos.
|
||||
* @return Un String con la representación XML formateada del objeto.
|
||||
* @throws JAXBException Si ocurre algún error durante la serialización.
|
||||
*/
|
||||
public static <T> String toXml(String namespaceUri, String localPart, Class<T> declaredType, T value) throws JAXBException {
|
||||
// 1. Crear el QName (Qualified Name) a partir del namespace y el nombre local.
|
||||
QName qName = new QName(namespaceUri, localPart);
|
||||
|
||||
// 2. Crear el JAXBElement, que envuelve el objeto de datos con su información de esquema XML.
|
||||
JAXBElement<T> jaxbElement = new JAXBElement<>(qName, declaredType, value);
|
||||
|
||||
// 3. Reutilizar el método original para hacer la conversión a String.
|
||||
return toXml(jaxbElement);
|
||||
}
|
||||
|
||||
/**
|
||||
* Convierte un objeto JAXBElement genérico en una representación de String con formato XML.
|
||||
* <p>
|
||||
* Este método es genérico y puede manejar cualquier tipo de objeto contenido dentro de un JAXBElement.
|
||||
* Utiliza una caché para las instancias de JAXBContext, optimizando el rendimiento al evitar
|
||||
* la recreación costosa de estos objetos.
|
||||
*
|
||||
* @param element El objeto JAXBElement que se va a convertir a XML. No puede ser nulo.
|
||||
* @param <T> El tipo del valor contenido en el JAXBElement.
|
||||
* @return Un String que representa el objeto en formato XML, indentado para fácil lectura.
|
||||
* @throws JAXBException Si ocurre un error durante el proceso de marshalling (conversión de objeto a XML).
|
||||
* Esto puede suceder si el contexto JAXB no se puede crear para la clase dada
|
||||
* o si hay un problema durante la serialización.
|
||||
*/
|
||||
public static <T> String toXml(JAXBElement<T> element) throws JAXBException {
|
||||
if (element == null) {
|
||||
// Es preferible devolver un string vacío o lanzar una excepción si el elemento es nulo.
|
||||
// Para un helper, lanzar IllegalArgumentException es una buena práctica.
|
||||
throw new IllegalArgumentException("El JAXBElement de entrada no puede ser nulo.");
|
||||
}
|
||||
|
||||
// Obtiene la clase del objeto contenido en el JAXBElement (por ejemplo, ReadCustomerProductsRq.class).
|
||||
Class<?> objectClass = element.getDeclaredType();
|
||||
|
||||
// Obtiene el JAXBContext de la caché o lo crea si no existe.
|
||||
// computeIfAbsent es una operación atómica que asegura que el contexto se cree solo una vez por clase.
|
||||
JAXBContext context = JAXB_CONTEXT_CACHE.computeIfAbsent(objectClass, clazz -> {
|
||||
try {
|
||||
return JAXBContext.newInstance(clazz);
|
||||
} catch (JAXBException e) {
|
||||
// Envuelve la excepción comprobada en una excepción de runtime para usarla dentro de la lambda.
|
||||
throw new RuntimeException("Error al crear la instancia de JAXBContext para la clase: " + clazz.getName(), e);
|
||||
}
|
||||
});
|
||||
|
||||
// Crea un Marshaller a partir del contexto. El Marshaller es el que realiza la conversión.
|
||||
Marshaller marshaller = context.createMarshaller();
|
||||
|
||||
// Configura la propiedad para que la salida XML esté formateada con indentación y saltos de línea.
|
||||
// Esto es clave para que el XML sea legible en los logs.
|
||||
marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE);
|
||||
|
||||
// Se utiliza StringWriter para escribir la salida XML en un String.
|
||||
StringWriter stringWriter = new StringWriter();
|
||||
|
||||
// Realiza la serialización del objeto JAXBElement y escribe el resultado en el StringWriter.
|
||||
marshaller.marshal(element, stringWriter);
|
||||
|
||||
// Devuelve el contenido del StringWriter como un String.
|
||||
return stringWriter.toString();
|
||||
}
|
||||
|
||||
}
|
||||
@ -0,0 +1,111 @@
|
||||
package com.banesco.common.infraestructure.repository;
|
||||
|
||||
import com.banesco.common.domain.model.BackResponse;
|
||||
import com.banesco.common.infraestructure.helpers.JsonHelper;
|
||||
import com.banesco.common.infraestructure.helpers.StringHelper;
|
||||
|
||||
import java.io.FileInputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.util.Arrays;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
|
||||
public class MessageRepository {
|
||||
|
||||
private static final Logger logger = Logger.getLogger(MessageRepository.class.getName());
|
||||
|
||||
/**
|
||||
* Respuesta de error por defecto que se utiliza cuando no se encuentra un
|
||||
* error específico.
|
||||
*/
|
||||
|
||||
/**
|
||||
* Mapa que almacena múltiples mapas de códigos de error, donde la clave
|
||||
* principal es el nombre del archivo de mensajes.
|
||||
*/
|
||||
public final Map<String, Map<String, BackResponse>> mapErrorsMultiple = new HashMap<>();
|
||||
|
||||
/**
|
||||
* Carga los mensajes de error desde un InputStream y los almacena en un
|
||||
* mapa.
|
||||
*
|
||||
* @param inputStream El InputStream que contiene los datos JSON de los
|
||||
* mensajes de error.
|
||||
* @param messageFileKey La clave del archivo de mensajes, utilizada para
|
||||
* almacenar el mapa en mapErrorsMultiple.
|
||||
* @return Un mapa que contiene los códigos de error como claves y los
|
||||
* objetos BackResponse como valores.
|
||||
* @throws IOException Si ocurre un error de entrada/salida al leer el
|
||||
* InputStream.
|
||||
*/
|
||||
private Map<String, BackResponse> loadFile(InputStream inputStream, String messageFileKey) throws IOException {
|
||||
Map<String, BackResponse> mapStatusCodes = new HashMap<>();
|
||||
Arrays.stream(JsonHelper.MAPPER.readValue(inputStream, BackResponse[].class)).forEach(o -> {
|
||||
mapStatusCodes.put(o.getBackendCode(), o);
|
||||
});
|
||||
mapErrorsMultiple.put(messageFileKey, mapStatusCodes);
|
||||
return mapStatusCodes;
|
||||
}
|
||||
|
||||
/**
|
||||
* Carga los mensajes de error desde una cadena JSON y los almacena en un
|
||||
* mapa.
|
||||
*
|
||||
* @param messageFileKey La clave del archivo de mensajes, utilizada para
|
||||
* almacenar el mapa en mapErrorsMultiple.
|
||||
* @param jsonString La cadena JSON que contiene los datos de los mensajes
|
||||
* de error.
|
||||
* @throws IOException Si ocurre un error al procesar la cadena JSON.
|
||||
*/
|
||||
public void loadMessagesFromString(String messageFileKey, String jsonString) throws IOException {
|
||||
Map<String, BackResponse> mapStatusCodes = new HashMap<>();
|
||||
Arrays.stream(JsonHelper.MAPPER.readValue(jsonString, BackResponse[].class)).forEach(o -> {
|
||||
mapStatusCodes.put(o.getBackendCode(), o);
|
||||
});
|
||||
mapErrorsMultiple.put(messageFileKey, mapStatusCodes);
|
||||
}
|
||||
|
||||
/**
|
||||
* Obtiene el mapa de códigos de error para un archivo de respuesta
|
||||
* específico.
|
||||
*
|
||||
* @param responseFile El nombre del archivo de respuesta para el cual se
|
||||
* desea obtener el mapa de errores.
|
||||
* @return Un mapa que contiene los códigos de error como claves y los
|
||||
* objetos BackResponse como valores, o null si no se encuentra el mapa.
|
||||
*/
|
||||
public Map<String, BackResponse> getErrorMap(String responseFile, boolean insideProperties) {
|
||||
Map<String, BackResponse> errorMap = mapErrorsMultiple.get(responseFile);
|
||||
if (insideProperties || (errorMap != null && !errorMap.isEmpty())) {
|
||||
return errorMap;
|
||||
}
|
||||
|
||||
String fileName = (StringHelper.isNumeric(responseFile) ? "vb".concat(responseFile) : responseFile).concat(".json");
|
||||
|
||||
try {
|
||||
try {
|
||||
// Intenta cargar el archivo desde el directorio /config/.
|
||||
return loadFile(new FileInputStream("/config/".concat(fileName)), responseFile);
|
||||
} catch (IOException e) {
|
||||
// Si no se encuentra el archivo en /config/, intenta cargarlo desde el classpath.
|
||||
logger.log(Level.WARNING, "Path /config/" + fileName + " not found. Loading local from errors-mapping/" + fileName);
|
||||
ClassLoader classLoader = getClass().getClassLoader();
|
||||
InputStream inputStream = classLoader.getResourceAsStream("errors-mapping/" + fileName);
|
||||
if (inputStream == null) {
|
||||
// Si no se encuentra el archivo en el classpath, registra un error y devuelve null.
|
||||
logger.log(Level.SEVERE, "Resource errors-mapping/" + fileName + " not found.");
|
||||
return null;
|
||||
}
|
||||
return loadFile(inputStream, responseFile);
|
||||
}
|
||||
} catch (IOException e) {
|
||||
// Si ocurre un error al cargar el archivo desde cualquier ubicación, registra un error y devuelve null.
|
||||
logger.log(Level.SEVERE, "Error getting Service Messages to /config/".concat(fileName) + ": " + e.getMessage());
|
||||
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,90 @@
|
||||
package com.banesco.common.infraestructure.repository;
|
||||
|
||||
import com.banesco.common.domain.model.ApiConfig;
|
||||
import com.banesco.common.infraestructure.helpers.JsonHelper;
|
||||
import com.banesco.common.infraestructure.helpers.LoggerHelper;
|
||||
|
||||
import java.io.BufferedReader;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStreamReader;
|
||||
import java.io.OutputStream;
|
||||
import java.net.HttpURLConnection;
|
||||
import java.net.URL;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
import java.util.concurrent.CompletableFuture;
|
||||
import java.util.concurrent.ExecutorService;
|
||||
import java.util.concurrent.Executors;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
|
||||
public class RegisterSecurityRepository {
|
||||
|
||||
private static final Logger logger = Logger.getLogger(RegisterSecurityRepository.class.getName());
|
||||
private final LoggerHelper loggerHelper;
|
||||
private final ApiConfig registerSecurityAPI;
|
||||
private final ExecutorService executor = Executors.newCachedThreadPool();
|
||||
|
||||
public RegisterSecurityRepository(LoggerHelper loggerHelper, ApiConfig registerSecurityAPI) {
|
||||
this.loggerHelper = loggerHelper;
|
||||
this.registerSecurityAPI = registerSecurityAPI;
|
||||
}
|
||||
|
||||
public <T> void writeTrice(String requestId, T registerSecurityRq) {
|
||||
logger.info(loggerHelper.buildInfoPrivateRequest(requestId, "RegisterSecurityRq", registerSecurityRq));
|
||||
|
||||
CompletableFuture.runAsync(() -> {
|
||||
try {
|
||||
URL url = new URL(registerSecurityAPI.getUrl());
|
||||
HttpURLConnection connection = (HttpURLConnection) url.openConnection();
|
||||
connection.setRequestMethod("POST");
|
||||
connection.setRequestProperty("Content-Type", "application/json");
|
||||
connection.setConnectTimeout(registerSecurityAPI.getTimeout().getConnect());
|
||||
connection.setReadTimeout(registerSecurityAPI.getTimeout().getResponse());
|
||||
connection.setDoOutput(true);
|
||||
|
||||
String jsonInputString = JsonHelper.getJsonFromObject(registerSecurityRq);
|
||||
|
||||
try (OutputStream os = connection.getOutputStream()) {
|
||||
byte[] input = jsonInputString.getBytes(StandardCharsets.UTF_8);
|
||||
os.write(input, 0, input.length);
|
||||
}
|
||||
|
||||
int responseCode = connection.getResponseCode();
|
||||
if (responseCode == HttpURLConnection.HTTP_OK) {
|
||||
try (BufferedReader br = new BufferedReader(new InputStreamReader(connection.getInputStream(), StandardCharsets.UTF_8))) {
|
||||
StringBuilder response = new StringBuilder();
|
||||
String responseLine;
|
||||
while ((responseLine = br.readLine()) != null) {
|
||||
response.append(responseLine.trim());
|
||||
}
|
||||
logger.info(loggerHelper.buildInfoPrivateResponse(requestId, "RegisterSecurityRs", response.toString()));
|
||||
}
|
||||
} else {
|
||||
try (BufferedReader br = new BufferedReader(new InputStreamReader(connection.getErrorStream(), StandardCharsets.UTF_8))) {
|
||||
StringBuilder response = new StringBuilder();
|
||||
String responseLine;
|
||||
while ((responseLine = br.readLine()) != null) {
|
||||
response.append(responseLine.trim());
|
||||
}
|
||||
logger.info(loggerHelper.buildInfoPrivateResponse(requestId, "RegisterSecurityRs", response.toString()));
|
||||
}
|
||||
}
|
||||
|
||||
connection.disconnect();
|
||||
|
||||
} catch (IOException e) {
|
||||
logger.log(Level.SEVERE, String.format("Error interno writeTrice: %s", e.getMessage()));
|
||||
logger.info(loggerHelper.buildInfoPrivateResponse(requestId, "RegisterSecurityRs", e.getMessage()));
|
||||
}
|
||||
}, executor).exceptionally(ex -> {
|
||||
logger.log(Level.SEVERE, String.format("Async Error interno writeTrice: %s", ex.getMessage()));
|
||||
logger.info(loggerHelper.buildInfoPrivateResponse(requestId, "RegisterSecurityRs", ex.getMessage()));
|
||||
return null;
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
public void shutdown() {
|
||||
executor.shutdown();
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,113 @@
|
||||
package com.banesco.common.infraestructure.service;
|
||||
|
||||
import com.banesco.common.domain.dto.bian.response.BianStatusResponse;
|
||||
import com.banesco.common.domain.model.BackResponse;
|
||||
import com.banesco.common.domain.model.StatusResponse;
|
||||
import com.banesco.common.infraestructure.repository.MessageRepository;
|
||||
|
||||
import java.util.Map;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
|
||||
public class MessageService {
|
||||
|
||||
private static final Logger logger = Logger.getLogger(MessageService.class.getName());
|
||||
private final MessageRepository messageRepository;
|
||||
|
||||
private final String CONFLICT = "CONFLICT";
|
||||
private final BackResponse DEFAULT_ERROR = new BackResponse(
|
||||
CONFLICT,
|
||||
409,
|
||||
CONFLICT,
|
||||
CONFLICT
|
||||
);
|
||||
|
||||
private boolean messagesInsideProperties = false;
|
||||
|
||||
/**
|
||||
* Constructor de MessageService.
|
||||
*
|
||||
* @param messageRepository El repositorio de mensajes que se utilizará para
|
||||
* cargar y obtener mensajes de error.
|
||||
*/
|
||||
public MessageService(MessageRepository messageRepository) {
|
||||
this.messageRepository = messageRepository;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Carga mensajes desde una cadena JSON en el repositorio de mensajes.
|
||||
*
|
||||
* @param responseFileName El nombre del archivo de respuesta asociado con
|
||||
* los mensajes.
|
||||
* @param jsonResponse La cadena JSON que contiene los mensajes.
|
||||
*/
|
||||
public void loadMessageFromJson(String responseFileName, String jsonResponse) {
|
||||
messagesInsideProperties = true;
|
||||
try {
|
||||
messageRepository.loadMessagesFromString(responseFileName, jsonResponse);
|
||||
} catch (Exception ex) {
|
||||
logger.log(Level.SEVERE, "Error loading messages from JSON: %s".formatted(ex.getMessage()), ex);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Obtiene una respuesta de estado (BackResponse) basada en el código de
|
||||
* backend y el nombre del archivo de respuesta.
|
||||
*
|
||||
* @param responseFileName El nombre del archivo de respuesta.
|
||||
* @param backendCode El código de backend para buscar la respuesta.
|
||||
* @return La respuesta de estado (BackResponse) correspondiente al código
|
||||
* de backend, la respuesta por defecto si no se encuentra, o null si hay un
|
||||
* error.
|
||||
*/
|
||||
public BackResponse geStatusResponse(String responseFileName, String backendCode) {
|
||||
logger.log(Level.INFO, "Finding backendCode: \"%s\" in File: \"%s\"".formatted(backendCode, responseFileName));
|
||||
Map<String, BackResponse> errors = messageRepository.getErrorMap(responseFileName, messagesInsideProperties);
|
||||
|
||||
if (errors == null || errors.isEmpty()) {
|
||||
logger.log(Level.WARNING, "Error map for %s is empty or null.".formatted(responseFileName));
|
||||
return DEFAULT_ERROR;
|
||||
}
|
||||
|
||||
BackResponse backResponse = null;
|
||||
try {
|
||||
backResponse = errors.get(backendCode);
|
||||
if (backResponse == null) {
|
||||
backResponse = errors.get("default");
|
||||
}
|
||||
} catch (Exception e) {
|
||||
logger.log(Level.WARNING, "Error code: %s not found in %s. Using default.".formatted(backendCode, responseFileName), e);
|
||||
try {
|
||||
backResponse = errors.get("default");
|
||||
} catch (Exception e2) {
|
||||
logger.log(Level.SEVERE, "Error getting default code.", e2);
|
||||
}
|
||||
}
|
||||
|
||||
if (backResponse == null) {
|
||||
logger.log(Level.WARNING, "Error code: %s and default not found in %s.".formatted(backendCode, responseFileName));
|
||||
return DEFAULT_ERROR;
|
||||
}
|
||||
return backResponse;
|
||||
}
|
||||
|
||||
public StatusResponse backToStatusResponse(BackResponse backResponse, String target) {
|
||||
return new StatusResponse(
|
||||
backResponse.getStatusCode(),
|
||||
target == null ? backResponse.getDescription() :
|
||||
backResponse.getDescription().formatted(target)
|
||||
);
|
||||
}
|
||||
|
||||
public BianStatusResponse backToBianStatusResponse(String traceId, BackResponse backResponse, String target) {
|
||||
return new BianStatusResponse(
|
||||
backResponse.getHttpCode() >= 200 && backResponse.getHttpCode() < 300 ? "ok" : "error",
|
||||
backResponse.getStatusCode(),
|
||||
target == null ? backResponse.getDescription() :
|
||||
backResponse.getDescription().formatted(target),
|
||||
traceId
|
||||
|
||||
);
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,90 @@
|
||||
package com.banesco.common.infraestructure.utils;
|
||||
|
||||
import java.time.DateTimeException;
|
||||
import java.time.LocalDate;
|
||||
import java.time.format.DateTimeFormatter;
|
||||
|
||||
/**
|
||||
* Clase para validación de fechas con configuración flexible. Permite validar
|
||||
* fechas en diferentes formatos, comprobar rangos de años y verificar la
|
||||
* correcta formación de componentes de fecha (año, mes, día). Implementa el
|
||||
* patrón Builder para facilitar la configuración personalizada de los
|
||||
* parámetros de validación.
|
||||
*/
|
||||
public class DateValidator {
|
||||
|
||||
private final DateTimeFormatter dateFormatter;
|
||||
private final PatternValidator datePattern;
|
||||
private final int minYear;
|
||||
private final int maxYear;
|
||||
|
||||
private DateValidator(Builder builder) {
|
||||
this.dateFormatter = builder.dateFormatter;
|
||||
this.datePattern = new PatternValidator(builder.dateFormatRegex);
|
||||
this.minYear = builder.minYear;
|
||||
this.maxYear = builder.maxYear;
|
||||
}
|
||||
|
||||
public static class Builder {
|
||||
|
||||
private DateTimeFormatter dateFormatter = DateTimeFormatter.ofPattern("yyyy/MM/dd");
|
||||
private String dateFormatRegex = "(\\d{4})/(0[1-9]|1[0-2])/(0[1-9]|[12][0-9]|3[01])";
|
||||
private int minYear = 1900;
|
||||
private int maxYear = 2100;
|
||||
|
||||
public Builder withDateFormatter(String dateFormatterPattern) {
|
||||
this.dateFormatter = DateTimeFormatter.ofPattern(dateFormatterPattern);
|
||||
return this;
|
||||
}
|
||||
|
||||
public Builder withDateFormatRegex(String dateFormatRegex) {
|
||||
this.dateFormatRegex = dateFormatRegex;
|
||||
return this;
|
||||
}
|
||||
|
||||
public Builder withMinYear(int minYear) {
|
||||
this.minYear = minYear;
|
||||
return this;
|
||||
}
|
||||
|
||||
public Builder withMaxYear(int maxYear) {
|
||||
this.maxYear = maxYear;
|
||||
return this;
|
||||
}
|
||||
|
||||
public DateValidator build() {
|
||||
return new DateValidator(this);
|
||||
}
|
||||
}
|
||||
|
||||
public boolean isValidDateFormat(String date) {
|
||||
return datePattern.isValid(date);
|
||||
}
|
||||
|
||||
public boolean isValidDate(String date) {
|
||||
if (!isValidDateFormat(date)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
try {
|
||||
LocalDate parsedDate = LocalDate.parse(date, dateFormatter);
|
||||
String formattedDate = parsedDate.format(dateFormatter);
|
||||
return date.equals(formattedDate);
|
||||
} catch (DateTimeException e) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
public boolean isValidDate(int year, int month, int day) {
|
||||
return year >= minYear && year <= maxYear && month >= 1 && month <= 12 && isValidDayOfMonth(year, month, day);
|
||||
}
|
||||
|
||||
private boolean isValidDayOfMonth(int year, int month, int day) {
|
||||
try {
|
||||
LocalDate.of(year, month, day);
|
||||
return true;
|
||||
} catch (DateTimeException e) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,32 @@
|
||||
package com.banesco.common.infraestructure.utils;
|
||||
|
||||
import java.util.regex.Pattern;
|
||||
|
||||
/**
|
||||
* Clase para validar Expresion regulares
|
||||
*/
|
||||
public class PatternValidator {
|
||||
|
||||
private final Pattern pattern;
|
||||
|
||||
public PatternValidator(String patternStr) {
|
||||
pattern = Pattern.compile(patternStr);
|
||||
}
|
||||
|
||||
public static PatternValidator withRegex(String patternStr) {
|
||||
return new PatternValidator(patternStr);
|
||||
}
|
||||
|
||||
/**
|
||||
* Validates is un valor tiene formato valido.
|
||||
*
|
||||
* @param value the value to check.
|
||||
* @return true if the value has format valid, false otherwise.
|
||||
*/
|
||||
public boolean isValid(String value) {
|
||||
if (value == null) {
|
||||
return false;
|
||||
}
|
||||
return pattern.matcher(value).matches();
|
||||
}
|
||||
}
|
||||
19
src/test/java/com/banesco/AppTest.java
Normal file
19
src/test/java/com/banesco/AppTest.java
Normal file
@ -0,0 +1,19 @@
|
||||
package com.banesco;
|
||||
|
||||
|
||||
/**
|
||||
* Unit test for simple App.
|
||||
*/
|
||||
public class AppTest {
|
||||
/**
|
||||
* Create the test case
|
||||
*
|
||||
* @param testName name of the test case
|
||||
*/
|
||||
|
||||
public AppTest(String testName) {
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
Loading…
x
Reference in New Issue
Block a user