bancolombia-scaffold-clean-architecture

repository·master·Indexed 19 days ago

https://github.com/bancolombia/scaffold-clean-architecture

A Gradle plugin that automates the scaffolding of Java applications based on Clean Architecture principles and Bancolombia's specific best practices. It organizes projects into four layers: Domain (business logic), Usecases (application logic), Infrastructure (Entry Points, Driven Adapters, and Helpers), and Application (module assembly and dependency injection via @ComponentScan).

Tokens
20K
Snippets
62
Records
100
Agent score
67%

What's inside scaffold-clean-architecture

  1. Scaffolding of Clean Architecture with the Gradle plugin

    master
    This project provides a Gradle plugin designed to scaffold Java applications following Clean Architecture principles and Bancolombia's best practices. It automates the creation of the project structure, ensuring consistency and adherence to architectural patterns.
  2. Understand the Dependency Rules for Clean Architecture

    master

    The validateStructure task enforces the Dependency Rule: source code dependencies can only point inwards. Inner circles must not know about anything in outer circles. The task enforces the following specific constraints:

    1. Model module: Must have no dependencies at all.
    2. UseCase module: Can only declare a dependency to the Model module. No other dependencies are allowed.
    3. Infrastructure Layer modules:
      • Can declare any external dependency.
      • Can declare dependencies on Model and/or UseCase modules.
      • Must avoid declaring a dependency on the AppService module.
  3. Understand the Clean Architecture structure in the Mongo example

    master

    The example-mongo project follows a Clean Architecture pattern organized into specific layers. The flow moves from external components (Infrastructure/Entry Points) towards the core business logic (Domain/Usecases), with the Application module acting as the orchestrator.

    Layer Breakdown:

    1. Domain: The innermost layer. It encapsulates business logic and rules using domain models and entities.
    2. Usecases: Part of the domain layer. It implements system use cases, defines application logic, and orchestrates flows by interacting with the Domain entities. It reacts to invocations from Entry Points.
    3. Infrastructure:
      • Helpers: General utilities for Driven Adapters and Entry Points. These use generics to model behaviors for various persistence objects (based on the Unit of Work and Repository patterns). They must be inherited by Driven Adapters.
      • Driven Adapters: Implementations of external systems, such as REST/SOAP services, databases (e.g., MongoDB), or file reading.
      • Entry Points: The entry points of the application where business flows begin.
    4. Application: The outermost layer. It assembles all modules, resolves dependencies, and starts the application (it contains the public static void main method).
  4. Understand the Clean Architecture structure in the Redis example

    master

    This project implements Clean Architecture by separating concerns into distinct layers. The architecture flows from the outermost layer (Application) to the innermost layer (Domain).

    • Domain: The innermost module. It encapsulates business logic and rules using domain models and entities.
    • Usecases: A Gradle module within the Domain layer. It implements system use cases, defines application logic, and orchestrates flows by interacting with the Domain entities. It reacts to invocations from Entry Points.
    • Infrastructure: Contains the technical implementation details, subdivided into:
      • Helpers: General utilities for Driven Adapters and Entry Points. These use generics to model behaviors for persistence objects (based on Unit of Work and Repository patterns) and must be inherited by Driven Adapters.
      • Driven Adapters: Implementations of external systems such as REST services, SOAP, databases, or file reading. They represent any external data source the system interacts with.
      • Entry Points: The entry points of the application or the starting points of business flows.
    • Application: The outermost module. It is responsible for assembling modules, resolving dependencies, and automatically creating Spring beans for Use Cases via @ComponentScan. This is the only module containing the public static void main(String[] args) method.
  5. Understand the Clean Architecture structure in the S3 Example

    master

    The project follows a layered Clean Architecture pattern, organized from the most external components to the core business logic. The layers are:

    1. Application: The outermost layer. It assembles modules, resolves dependencies, and starts the application (contains the public static void main method). It uses @ComponentScan to automatically register UseCase beans.
    2. Entry Points: Represent the entry points of the application or the start of business flows.
    3. Driven Adapters: Implementations of external systems such as REST/SOAP services, databases, or file reading (e.g., S3 interaction).
    4. Infrastructure (Helpers): Contains general utilities for Driven Adapters and Entry Points. These use generics and follow patterns like Unit of Work and Repository. Helpers must be inherited by Driven Adapters.
    5. Usecases: Implements system use cases and application logic. It orchestrates flows by calling the Entities module and reacts to invocations from Entry Points.
    6. Domain (Entities): The innermost module. It encapsulates business rules and logic through domain models and entities.
  6. Understand the Clean Architecture layers

    master

    The Scaffold Clean Architecture Gradle Plugin generates a multi-module project following Robert C. Martin's Clean Architecture principles. The architecture is organized into three main layers where dependencies always point inwards:

    1. Domain (Internal): Encapsulates business rules and logic.

      • model module: Contains domain models, entities, and defines ports (interfaces).
      • usecase module: Contains application logic and orchestrates flows using the ports defined in the model module.
    2. Infrastructure (Middle): Contains technical implementations of the domain ports.

      • entry-points modules: The start of business flows (e.g., REST controllers, Kafka consumers).
      • driven-adapters modules: External implementations (e.g., database connections, REST/SOAP clients, file readers).
      • helpers modules: General utilities for Driven Adapters and Entry Points.
    3. Application (External): The outermost layer responsible for assembling modules, resolving dependencies, and creating beans. This is the only module containing the public static void main(String[] args) method to start the application.

  7. Understand the Clean Architecture structure

    master

    The project follows a Clean Architecture pattern organized into specific layers to isolate business logic from external details. The layers are organized from the most internal (core business) to the most external (infrastructure and application assembly):

    1. Domain: The innermost layer. It encapsulates business logic and rules using domain models and entities.
    2. Usecases: A Gradle module within the domain layer. It implements system use cases, defines application logic, and orchestrates flows by interacting with the Domain entities. It reacts to invocations from Entry Points.
    3. Infrastructure: Contains the technical implementations required by the system.
      • Helpers: General utilities for Driven Adapters and Entry Points. These use generics to model behaviors for various persistence objects (based on the Unit of Work and Repository patterns). Helpers must be inherited by Driven Adapters.
      • Driven Adapters: Implementations of external systems, such as REST/SOAP services, databases, or file readers.
      • Entry Points: The entry points of the application that initiate business flows.
    4. Application: The outermost layer. It is responsible for assembling modules, resolving dependencies, and automatically creating Spring beans for the Use Cases. This is the only module containing the public static void main(String[] args) method.
  8. How UseCase beans are automatically registered in the Application layer

    master
    In this scaffold, you do not need to manually define every bean for your business logic. The Application module is configured with a @ComponentScan annotation. This allows the framework to automatically discover and instantiate UseCase beans and inject their required dependencies (such as Driven Adapters) during the application startup.
  9. Ensure UseCases and Beans use final attributes for concurrency safety

    master

    To avoid concurrency issues caused by shared mutable state, ArchUnit enforces that all dependencies in UseCase classes and Spring @Component (Beans) must be immutable.

    • UseCases: All attributes must be declared as final.
    • Beans: Dependencies should be injected via constructor rather than using @Value on fields. This ensures all dependencies are final and immutable.
    // Compliant Bean using constructor injection
    @Component
    public class MyService {
        private final String endpoint;
    
        public MyService(@Value("${external-service.endpoint}") String endpoint) {
            this.endpoint = endpoint;
        }
    }
  10. Implement Driven Adapters and Helpers

    master

    Driven Adapters and Helpers are part of the Infrastructure layer.

    • Driven Adapters: Use these to implement interactions with external sources like databases, REST/SOAP services, or flat files.
    • Helpers: Provide generic utilities for Driven Adapters and Entry Points. These utilities are not tied to concrete objects and use generics to model behaviors for various persistence objects (based on the Unit of Work and Repository patterns).

    Note: Helper classes cannot exist in isolation; they must be inherited/used within Driven Adapters.

  11. Template variables for module generation

    master

    Modules are generated using Mustache templates. The following variables are available to impact template generation:

    Boolean Variables:

    • lombok: Enables/disables Lombok annotations (default: true).
    • metrics: Enables/disables metric generation (default: true).
    • reactive: Determines if the module is reactive. If true, the resource directory follows the <module-name>-reactive pattern; otherwise, it uses <module-name> (default: false).

    Predefined Variables:

    • projectName: The name assigned by the user.
    • projectNameLower: The project name in lowercase.
    • package: The user-defined package (e.g., co.com.bancolombia.sample).
    • packagePath: The package path (e.g., co/com/bancolombia/sample).
    • Constants: Any constant defined in the Constants class is available by its name (e.g., PLUGIN_VERSION).