MS Template
- Microservice template.
- Has Postgres database
Integrations
Origin | Target | Operation | HTTP METHOD |
---|---|---|---|
External services | system-x | /api/v2/orderManagement/entityX | GET |
Config map
Telemetry
- spring.sleuth.otel.exporter.otlp.endpoint=#ex.http://localhost:4317 sleuth endpoint
- spring.sleuth.otel.config.trace-id-ratio-based= #ex:0.0- 0% rate / 1.0 - 100% rate
DATABASE
- spring.datasource.url=#ex. jdbc:postgresql://localhost:5432/catalogdomain
- spring.datasource.username=#ex. admin
- spring.datasource.password=#ex. admin
Environment Parametrization
External System Endpoints
Events
- event.processing.kafka.address=#ex. localhost:9092 Kafka Address
- event.processing.queue.business=#ex. event-tracing Topic for business event
- event.processing.queue.message=#ex. event-tracing Topic for message event
- event.processing.queue.application=#ex. event-tracing Topic for application event
- event.processing.client.producer.enable=#ex. false values true/false parameter to on/of publish event to kafka
Logging
- modules.logging.message.enable = ex: true
- modules.logging.message.configuration = ex: EVENT #listOfValues: CONSOLE,DB,EVENT
- modules.logging.application.enable = ex: true
- modules.logging.application.level = ex: ERROR #listOfValues: ERROR,DEBUG,WARN
- modules.logging.application.configuration = ex:{'':'CONSOLE,EVENT'} ##listOfValues {'':{'CONSOLE','DB','FULL','EVENT'}}
Business Configuration
Domain Orchestration Template
Project Structure:
Note: com.readinessit.microservice should be replaced by the customer domain when working on customer project
com
└── readinessit.microservice.template -> root folder should only have application
├── adapters -> contains all external system related classes
| ├── externalsystem(customer) -> contains classes related to this system, for example generic filling of header structures and error handling and interpretation
| └── dto -> all external structures devided by corresponding system
| └── crm -> data structure for external system crm
└── configuration -> implementation specific spring boot configuration on startup
| └── security -> spring configuration related to security
└── ece -> External Communication Engine - engine for all outbound communication (adapters)
| ├── action -> All implementations of the action service divided by type
| | ├── courier -> All actions related with external system communication
| | ├── handler -> All actions that will handle a request or response validation/mapping
| | └── mapper -> All actions related to mapping data from/to dtos
| ├── condition -> All implementations of the condition service
| └── service -> Any service related to a common pipeline implementation, tha can be executed anywhere in the code
└── domain/functionality -> Specific entity/domain for example an entity or a domain like customer domain
├── controller -> Exposed services to the exterior
├── entity -> Table entity class
├── persistence -> Repository class
└── service -> Logic to interact with the entity/domain
ECE Guidelines
- An ECE interaction is usually defined by a pipeline execution of 3 actions as follows:
- a mapper ("PRE_RUN_ACTION_ID") that maps the controller request DTO to the external system request DTO structure;
- a courier ("EXECUTION_ACTION_ID") to make the actual call to the external system;
- an handler ("POST_RUN_ACTION_ID") to treat the external system response DTO and apply business logic and/or map the information to the execution context or final response;
- A Courier action must only contain the logic for the actual external system call. No mappings or data validation -> this must be done in a Mapper action; No business logic or response handling -> this must be done in an Handler action;
- A Courier action external system call must be done via an Adapter;
- A Mapper action should only do request info validation and/or map information from a DTO to the execution context or another DTO;
- An Handler action should handle all business logic and/or the external system response validations and mapping to the execution context;
- A pipeline may be one single execution or be composed of several execution steps in an ordered sequence;
- A pipeline execution may be one handler or sequence up to 3 handlers, a mapper or a sequence up to 3 mappers or an external system call (as explained above);
- Any action may (and should) be used in multiple pipeline executions, wherever the same logic applies;
HOW TO DEVELOP AN ECE INTERFACE
With the "EXECUTION_CODE" being the "baseService.operation" name defined in a controller: (ex: CustomerRequest.createCustomerRequest)
- configure the new service in the OC_SERVICES table;
- configure the pipeline in the correct sequence ("EXECUTION_INDEX"), in the OC_EXECUTION_PIPELINE table.
- each step is defined by a "PIPELINE_ID" and the "STATUS" (0 or 1) defines if the step is active for execution;
- if a step must be executed on condition, define the condition class path in "EXECUTION_CONDITION";
- (if it does not exist already) configure each individual pipeline step ("PIPELINE_ID") in the OC_PIPELINE_DEFINITION table.
- pipeline executions may (and should) be used in multiple pipelines definitions;
- an ECE interaction is usually defined by a pipeline execution of 3 actions as follows:
- a mapper ("PRE_RUN_ACTION_ID") that maps the controller request DTO to the external system request DTO structure;
- a courier ("EXECUTION_ACTION_ID") to make the actual call to the external system;
- an handler ("POST_RUN_ACTION_ID") to treat the external system response DTO and apply business logic and/or map the information to the execution context or final response;
- a pipeline execution may also be just composed of handler(s) action(s) for business logic ("EXECUTION_ACTION_ID");
- a pipeline execution may also be just composed of mapper(s) action(s) for the pipeline ("EXECUTION_ACTION_ID"); example: a multiple executions pipeline final execution being a mapper to the controller's request final response DTO;
- (if it does not exist already) configure the class path of each individual pipeline execution action ("EXECUTION_ACTION_ID") in the OC_ACTION_DEFINITION table;
- actions may (and should) be used in multiple pipelines executions;
- (if it does not exist already) configure the external system interface information to be used by the adapter for the actual messaging communication in the OC_ADAPTER_DEFINITION;
- for each adapter interface definition: configure the endpoint of the interface for each environment in the OC_ADAPTER_ENDPOINT table;
HOW TO generate liquibase changeset
If you are creating or updating an existing table you will need to generate a loquibase changeset, to perform this you will need to do the following:
- mvn clean
- mvn compile
- mvn liquibase:diff
This will generate a new file under resources\db\changelog something like 20220811103406_entity_update.xml
- Add a more user-friendly message than, entity_update example update_tableName or create_tableName
HOW TO UPDATE THE DATABASE
Is it a new Virtual Configuration Table?
- create the table data csv file in the resources\db\data folder;
- generate/create the liquibase changeset in the resources\db\changelog\data folder;
- include the DB update in the liquibase file: resources\db\master.xml file;
Is it a new Configuration Table?
- create all the necessary JPA entities, repositories, etc;
- generate/create the liquibase changeset for the table creation in the resources\db\changelog\structure folder;
- include the DB update in the liquibase file: resources\db\master.xml file;
- create the table data csv file in the resources\db\data folder;
- generate/create the liquibase changeset in the resources\db\changelog\data folder;
- include the DB update in the liquibase file: resources\db\master.xml file under update data;
Is it a structure update to an existing table?
- update all the necessary JPA entities, repositories, etc;
- generate/create the liquibase changeset for the table update in the resources\db\changelog\structure folder;
- include the DB update in the liquibase file: resources\db\master.xml file under update structure;
Is it a data update to an existing table?
- just update the respective resources\db\data*.csv file
HOW TO CREATE A NEW CONTROLLER
- Always create a interface class that contains all the relevant operation details
- Request Parameters / Headers
- Request structure
- ExecutionContextDTO
- Httpcodes with there corresponding output structure ex: 200 SuccessDto, 400 ErrorDto
- Implementation class for the created interface, this class will contain the following
- Add @RestController annotation to the class
- Add @RequestMapping annotation with the path to the api to the class
- Add @ControllerECE annotation to each implemented method
- The response is always ResponseEntity without the type declaration ex:ResponseEntity in interface equals to ResponseEntity in implementation, this allows you to responde with error structure on error
HOW TO RUN THE UNIT TESTS
Note: unit tests must be run after every implementation to assure regression
Either:
- run the test maven command
or
- right-click the test\java folder and choose "Run/Debug All Tests";
A single specific unit test may be run individually by right-clicking the implementing class and choosing "Run/Debug Test";
---agregado