Dew Microservices Ecosystem

repository·master·Indexed 19 days ago

https://github.com/gudaoxuri/dew

A microservices ecosystem featuring the Dew DevOps Maven Plugin for integrating DevOps capabilities into the Maven build lifecycle. It provides support for Kubernetes containerized microservices, Spring Boot 2.x, MQTT, Redis, and various CI/CD integrations including GitLab CI and Jenkins Pipelines. The ecosystem includes release channels ranging from Alpha to GA and provides tools for leader election, distributed locking, and observability via Prometheus, Grafana, and Jaeger.

Tokens
35.6K
Snippets
91
Records
128
Agent score
58%

What's inside Dew

  1. Overview of the Dew Microservice System

    master

    Dew is a one-stop microservice solution designed to provide architecture guidance and extend mainstream microservice frameworks. Its core philosophy is to be transparent and unobtrusive, allowing developers to focus on business logic rather than the underlying framework complexity.

    Key Features

    • Architecture Guidance: Provides design principles for microservices.
    • Framework Extension: Extends Spring Boot to be compatible with both standard Spring environments and Service Mesh.
    • Design Principles:
      • Simple: Uses standard, familiar development models.
      • Comprehensive: Reuses existing market capabilities to reduce maintenance.
      • Lightweight: Avoids highly intrusive third-party libraries.
      • Replaceable: Focuses on extensions rather than modifying base framework code.
  2. Overview of the Dew SDK Maven Plugin

    master

    The Dew SDK Maven Plugin is a component of the Dew microservice ecosystem. It automates the generation of SDKs based on OpenAPI V3 specifications (via Swagger) and handles their automatic upload to a Maven repository.

    Supported Languages: Currently, only Java is supported. Support for additional languages is planned for future releases.

  3. Configure DevOps using .dew and Maven

    master

    Dew DevOps configuration is managed through two distinct channels:

    1. .dew files: Use these for relatively static, non-sensitive information (e.g., application replicas, port numbers, health check paths).
    2. Maven parameters: Use these for sensitive or environment-specific information passed via the command line (mvn -Dxxx) or defined in pom.xml properties (e.g., Kubernetes configurations, Harbor credentials).

    Best Practice: Keep non-sensitive defaults in .dew and inject secrets/environment-specific overrides via Maven.

  4. Manage JVM memory settings via container resource limits

    master

    Dew manages JVM parameters automatically based on the container resource limits defined in app.containerResourcesLimits and app.containerResourcesRequests.

    While you can manually set -Xms or -Xmx in app.runOptions, Dew provides a more automated way to manage memory using the following priority and rules:

    1. Manual Override: If JAVA_OPTIONS contains -Xmx or -Xms, those values are used first.
    2. Memory Ratio: If JAVA_MAX_MEM_RATIO is provided, -Xmx is set to (Max Available Memory) / JAVA_MAX_MEM_RATIO. (e.g., a ratio of 50 sets -Xmx to 50% of available memory).
    3. Automatic Scaling (if no ratio provided):
      • If system memory $\le$ 300M: -Xmx is set to 25% of available memory.
      • If system memory $>$ 300M: -Xmx is set to 50% of available memory.
    4. Initial Memory (-Xms):
      • If JAVA_INIT_MEM_RATIO is 0, -Xms is not set.
      • If JAVA_INIT_MEM_RATIO is non-zero, -Xms is set to -Xmx / JAVA_INIT_MEM_RATIO.
      • If JAVA_INIT_MEM_RATIO is not provided, it defaults to 100 (making -Xms equal to -Xmx).
  5. Configure and use Cluster capabilities

    master

    Dew provides abstracted interfaces for distributed capabilities, supporting Redis, Hazelcast, and RabbitMQ.

    Supported Features by Implementation

    |= | Feature | Redis | Hazelcast | Rabbit | MQTT | Distributed Cache | * | | | | Distributed Map | * | * | | | Distributed Lock | * | * | | | MQ | * | * | * | * (pub-sub only) | Leader Election | * | | | |=

    Enabling Cluster Support

    1. Add boot-starter.
    2. Add a specific SPI dependency (e.g., cluster-spi-redis).
    3. Configure the implementation in application.yml under dew.cluster.

    Distributed Cache

    Access via Dew.cluster.cache.

    Dew.cluster.cache.set("key", "value", 1);
    String val = $.json.toJson(Dew.cluster.cache.get("key"));

    Distributed Map

    Create named instances of distributed maps.

    ClusterMap<TestMapObj> mapObj = Dew.cluster.map.instance("test_obj_map", TestMapObj.class);
    mapObj.put("test", new TestMapObj());

    Distributed Lock

    Use tryLock or the simplified tryLockWithFun to ensure automatic unlocking.

    ClusterLock lock = Dew.cluster.lock.instance("test_lock");
    // Automatically unlocks after 1s if not manually released
    if (lock.tryLock(0, 1000)) {
        try {
            // business logic
        } finally {
            lock.unLock();
        }
    }
    
    // Simplified version
    lock.tryLockWithFun(0, 1000, () -> {
        // business logic (auto-unlocks)
    });

    Message Queue (MQ)

    Supports pub-sub and req-resp patterns.

    // Pub-Sub
    Dew.cluster.mq.subscribe("topic", msg -> logger.info(msg.getBody()));
    Dew.cluster.mq.publish("topic", "payload");
    
    // Req-Resp
    Dew.cluster.mq.response("topic", msg -> logger.info(msg.getBody()));
    Dew.cluster.mq.request("topic", "request_data");

    Note: For pub-sub, the topic must exist; subscribe will create it automatically.

    Leader Election

    ClusterElection election = Dew.cluster.election.instance("election_name");
    if (election.isLeader()) {
        // perform leader tasks
    }
    // Distributed Lock Example
    ClusterLock lock = Dew.cluster.lock.instance("my_lock");
    lock.tryLockWithFun(0, 5000, () -> {
        // Critical section
    });
  6. Configure Authentication Cache

    master

    Dew supports an authentication cache that allows business systems to cache login information generated by an external authentication system. This requires a cluster cache implementation (e.g., Redis).

    Configuration

    Configure token behavior in dew.security:

    • token-flag: The header/parameter name for the token (default: X-Dew-Token).
    • token-in-header: If true, token is in header; otherwise, in URL parameters.
    • token-kinds: Define different token types (e.g., PC, Android) with specific expire-sec and revision-history-limit.

    Using OptInfo

    OptInfo is the base class for login information. You can extend it to include custom user attributes.

    Important: If you use a custom subclass of OptInfo, you must register it at startup using DewContext.setOptInfoClazz(YourCustomClass.class).

    API Workflow

    1. Login: After successful authentication, call Dew.auth.setOptInfo(optInfo).
    2. Access: In subsequent requests, call Dew.context().optInfo() to retrieve the user info.
    3. Logout: Call Dew.auth.removeOptInfo().

    Custom Auth Adapter

    If the default Redis-based adapter is insufficient, implement the AuthAdapter interface and register it:

    Dew.auth = new CustomAuthAdapter();
    // Setting login info
    Dew.auth.setOptInfo(new OptInfoExt()
        .setAccountCode("user123")
        .setToken(token));
    
    // Retrieving login info
    Optional<OptInfoExt> info = Dew.auth.getOptInfo();
  7. Implement Unified Response with Resp

    master

    Dew recommends using a protocol-agnostic response format via the Resp class. This ensures consistency across HTTP, RPC, and MQ interactions.

    Response Format

    {
        "code": "", // Response code (e.g., 200 for success)
        "message": "", // Error description or status message
        "body": // Response payload
    }

    Usage

    public Resp<String> myMethod() {
        return Resp.success("Success Data");
        // or
        return Resp.notFound("Not Found");
    }

    HTTP Status Codes and Fallbacks

    • Resp codes are independent of HTTP status codes. Usually, HTTP status is 200.
    • To trigger a circuit breaker (like Hystrix) to treat a response as a failure, use .fallback().
    • Resp.serverError("msg") returns HTTP 200 with a body containing code: 500.
    • Resp.serverError("msg").fallback() returns HTTP 500.
    • The framework automatically converts all 5xx exceptions into HTTP 500 status codes.
    public Resp<String> test() {
        return Resp.success("enjoy!");
    }
    
    // To force an HTTP 500 for circuit breaking:
    public Resp<String> error() {
        return Resp.serverError("Critical Error").fallback();
    }
  8. Dew Project Structure and Modules

    master

    The Dew project is organized into several functional areas. Developers can leverage specific starters and modules depending on their microservice needs:

    Framework Modules (framework/modules)

    • parent-starter: The parent POM module.
    • boot-starter: Core module containing Spring Boot Web dependencies.
    • Cluster Capabilities: Interfaces and implementations for various clustering technologies:
      • cluster-common: Cluster capability interfaces.
      • cluster-hazelcast: Hazelcast implementation.
      • cluster-rabbit: RabbitMQ implementation.
      • cluster-redis: Redis implementation.
      • cluster-mqtt: MQTT implementation.
      • cluster-rocket: Rocket MQ implementation.
      • cluster-skywalking: Skywalking implementation.
    • Utility Starters:
      • idempotent-starter: Idempotency handling.
      • dbutils-starter: Dynamic database processing.
      • ossutils-starter: OSS (Object Storage Service) processing.
      • hbase-starter: Spring Boot HBase integration.
      • test-starter: Unit testing support.

    DevOps and Tools

    • sdkgen-maven-plugin: Plugin for automatic SDK generation and uploading.
    • devops: Contains Maven plugins (dew-maven-plugin, dew-maven-agent), execution scripts, and CI/CD configurations (GitLab CI, Jenkins).
  9. What happens during project creation with dew-devops.sh

    master

    When you execute sh dew-devops.sh, the Dew DevOps plugin automates the following infrastructure provisioning:

    • Harbor: Creates a Harbor project and a corresponding user with appropriate permission bindings.
    • Kubernetes Namespace: Creates a new namespace for the project.
    • Service Discovery: Binds the service-discovery-client role to the namespace to enable service-to-service discovery.
    • Registry Authentication: Creates a docker-registry Secret in the Kubernetes namespace for Harbor authentication.
    • Ingress: Creates a Kubernetes Ingress to bind services to specific domains (e.g., mapping api-uat.idealworld.group to the kernel service and uat.dew.idealworld.group to the frontend service).
  10. Understand .dew configuration inheritance rules

    master

    Dew supports a hierarchical configuration model:

    1. Global vs. Local: A .dew file placed in the project root (next to the parent pom.xml) acts as a global configuration. A .dew file placed in a specific module directory (next to the module's pom.xml) acts as a local configuration for that module.
    2. Inheritance: Modules inherit settings from the global .dew. Local settings override global settings.
    3. Profile Inheritance: If a global configuration defines a specific profile (e.g., uat), a module can override specific parameters within that same profile.

    Example Hierarchy:

    • Global .dew defines app.replicas: 1 and profiles.uat.namespace: todo-uat.
    • Module .dew defines profiles.uat.app.replicas: 2.
    • Result for Module: replicas is 1 (from global), but for the uat profile, replicas becomes 2 and namespace remains todo-uat.
  11. What happens during deployment with mvn -P devops

    master

    When you execute mvn -P devops deploy -Ddew_devops_profile=<profile>, the plugin performs an intelligent deployment workflow:

    1. Dependency Analysis: Identifies all Maven modules from the root pom.xml and sorts them by dependency order.
    2. Change Detection: Compares the current Git commit against the last deployed version to identify changed files.
    3. Module Filtering: Determines which modules need deployment based on the detected changes.
    4. Preparation & Build:
      • JVM Services (Spring Boot): Runs mvn package spring-boot-maven-plugin:repackage to create a fat JAR.
      • Frontend Projects: Runs npm install, installs @tarojs/cli, sets NODE_ENV=test, and executes npm run build:h5 to generate the dist folder.
    5. Containerization: Executes docker build and docker push to publish images to Harbor for both JVM services and frontend projects.
    6. Deployment:
      • JVM Libraries/Pom Projects: Runs mvn deploy to the Maven repository and creates a ConfigMap to record the version.
      • JVM Services/Frontend Projects: Deploys the deployment and service to Kubernetes and creates a ConfigMap to record the version.
  12. Recommended Project Structure for Dew

    master

    Dew recommends a specific hierarchical structure for large-scale projects to separate build logic, core services, SDKs, terminals, and documentation.

    Key components include:

    • sources/basics: Core dependencies (parent, common, common-service) that must be deployed to a Maven repository.
    • sources/services: Individual microservices.
    • sources/sdk: Language-specific SDKs (Java, JS, REST, etc.).
    • sources/terminals: Client applications (Android, iOS, WeChat, etc.).
    • docs: Documentation managed via Asciidoc and Maven.
    • env: Environment configurations (e.g., Spring Cloud Config stored in Git).
    • .gitmodules: Defines Git submodules for all constituent projects.
    ----
    X Build Project
    |- sources
    |  |- basics
    |  |  |- parent
    |  |  |- common
    |  |  |- common-service
    |  |  |- <...>
    |  |- services
    |  |  |- <service 1>
    |  |  |- <service ...>
    |  |- sdk
    |  |  |- <java>
    |  |  |- <js>
    |  |  |- <rest>
    |  |  |- <...>
    |  |- terminals
    |  |  |- <android>
    |  |  |- <ios>
    |  |  |- <wechat>
    |  |  |- <...>
    |  |- docs
    |  |  |- src
    |  |  |  |- main
    |  |  |  |  |- asciidoc
    |  |  |  |  |  |- book.adoc
    |  |  |  |  |  |- <...>
    |  |  |  |  |- resources
    |  |  |  |  |  |- images
    |  |  |  |  |  |- <...>
    |  |  |  |- pom.xml
    |  |  |- .gitignore
    |  |- env
    |  |  |- application.yml
    |  |  |- <...>
    |  |  |- .gitignore
    |  |- pom.xml
    | .gitmodules
    | .gitignore
    | README.adoc
    ----