Getting Started with the Milesoft Platform

This guide provides a comprehensive, zero-to-one walkthrough for bootstrapping, configuring, and running a brand-new backend application on the Milesoft Platform. By following this guide, you will initialize a Java 17+ Spring Boot microservice, configure the core Milesoft stack, integrate Google Cloud credentials, manage environments and secrets, and extend foundational platform configuration classes.


1. Bootstrapping Your Application with the CLI

The Milesoft CLI provides a high-performance boilerplate generator through the milesoft init command. This command sets up a fully scaffolded backend project (following our -app architecture convention) pre-configured with the standard directory structure, Gradle build files, base properties, and security configurations.

1.1 Command Execution

Open your terminal and run:

milesoft init my-innovative-app

1.2 Configuration Prompting

During initialization, the CLI interactive prompt will ask you to supply several environmental parameters to bind your application to the central gateway and secure its Google Cloud resources:

  • GCP Project ID: The primary Google Cloud Project (e.g., my-app-sand) where your runtime services—such as Secret Manager, Pub/Sub, Cloud Tasks, and Vertex AI—are located.
  • Milesoft Platform Modules: Toggle and select optional SDK clients and extension modules you want to include (e.g., Stripe, Twilio, Shopify Liquid templates, Vertex AI).

2. Scaffolded Project Architecture

The CLI generates a clean, standardized Spring Boot structure. Here is a high-level overview of the bootstrapped directory layout:

my-innovative-app/
├── build.gradle                   # Gradle plugins, repositories, and dependency declarations
├── settings.gradle                # Gradle root project settings
├── gradlew                        # Gradle wrapper script for Unix-based systems
├── gradlew.bat                    # Gradle wrapper script for Windows
├── Dockerfile                     # Containerization instructions for deployment
├── cloudbuild.yaml                # Google Cloud Build deployment pipeline script
└── src/
    ├── main/
    │   ├── java/
    │   │   └── com/yourcompany/myapp/
    │   │       ├── Application.java      # Spring Boot main class entry point
    │   │       └── config/               # Concrete beans extending platform abstract configs
    │   │           ├── AccountsConfig.java
    │   │           ├── AuthConfig.java
    │   │           └── SecretsConfig.java
    │   └── resources/
    │       ├── application.properties             # Base settings and gateway baseUrl variables
    │       ├── application.private.properties     # GIT-IGNORED: Local default secret overrides
    │       ├── application-sand.properties         # Sandbox/Staging GCP environment profiles
    │       └── application-sand.private.properties # GIT-IGNORED: Local sandbox secret overrides
    └── test/
        └── java/
            └── com/yourcompany/myapp/
                └── TestApplication.java   # Base context verification test

3. In-Depth Configuration & Build Setup

3.1 Dependencies and Build Setup (build.gradle)

The scaffolded build file applies the GCP Artifact Registry plugin and declares dependencies on core Milesoft stack foundation libraries. Note that Milesoft modules resolve from the secure read-only milesoft-repo registry:

plugins {
    id "com.google.cloud.artifactregistry.gradle-plugin" version "2.2.5"
    id "java"
    id "org.springframework.boot" version "3.5.15"
}

repositories {
    mavenLocal()       // Checked first for local offline development overrides
    mavenCentral()
    maven {
        // Secure Artifact Registry URL containing Milesoft SDKs
        url "artifactregistry://us-west2-maven.pkg.dev/milesoft-repo/repo-maven"
    }
}

dependencies {
    // Ingest the base application stack runtime framework
    implementation "io.milesoft:app-stack:2.2.0"
    
    // Ingest specific platform service SDKs based on CLI prompt selections
    implementation "io.milesoft:liquid-sdk:2.1.0"
    implementation "io.milesoft:contacts-sdk:2.0.1"
    
    // Ingest platform utility extensions
    implementation "io.milesoft:storage-ext:2.0.1"
    implementation "io.milesoft:task-queue-ext:2.0.1"
    implementation "io.milesoft:vertex-ext:2.0.1"
    
    // Standard testing dependencies
    testImplementation "junit:junit:4.13.2"
    testImplementation "org.mockito:mockito-core:5.21.0"
    testImplementation "io.milesoft:openpojo-ext:2.0.1"
}

java {
    sourceCompatibility = JavaVersion.VERSION_17
    targetCompatibility = JavaVersion.VERSION_17
}

3.2 Main Properties (application.properties)

The central properties file configures non-sensitive default values, routes traffic to central platform microservices, and defines Secret Manager placeholders:

# Logging Configurations
logging.level.root=INFO
logging.level.io.milesoft=DEBUG
logging.level.com.yourcompany.myapp=DEBUG

# Platform Gateway Services Base URLs
baseUrl.accounts=https://accounts.milesoft.api
baseUrl.notifications=https://notifications.milesoft.api
baseUrl.liquid=https://liquid.milesoft.api
baseUrl.contacts=https://contacts.milesoft.api

# Platform Secret Placeholders (Resolved via Secret Manager or Local Overrides)
secrets.milesoft.apiKey=milesoft_apiKey
secrets.milesoft.token=milesoft_token
secrets.encryption.password=encryption_password
secrets.encryption.salt=encryption_salt

# Active Spring Profile (e.g., sand for local sandbox development)
spring.profiles.active=sand

3.3 GCP Environment Profiles (application-sand.properties)

Environment-specific properties files (such as application-sand.properties for staging or application-prod.properties for production) specify target Google Cloud projects and configurations:

# Application & Auth Identifiers
app.id=my-app-id
account.id=my-sandbox-account-id
user.id=my-sandbox-admin-user-id

# Google Cloud Platform Infrastructure Configuration
secrets.project=my-app-sand
pubSub.project=my-app-sand
taskQueue.project=my-app-sand
vertex.project=my-app-sand

# Storage Configuration
storage.bucket=my-app-sand-documents

# Vertex AI Settings
vertex.location=us-central1
vertex.model=gemini-3.5-flash

4. Secret Management & Local Development Overrides

The Milesoft Secrets Extension (secrets-ext) acts as a secure decorator around Google Cloud Secret Manager. It simplifies operations by loading secrets dynamically at runtime without hardcoding sensitive strings into files that get committed to git repositories.

4.1 How Secret Resolution Works

In application.properties, properties matching the prefix secrets. are assigned key values (e.g. secrets.milesoft.apiKey=milesoft_apiKey). At startup:

  1. secrets-ext queries Secret Manager in the specified secrets.project (e.g., my-app-sand).
  2. It fetches the secret named milesoft_apiKey and transparently injects its decrypted payload into your Spring context as the active value of ${secrets.milesoft.apiKey}.

4.2 Local Development with Zero-Dependency Overrides

Connecting to GCP services during fast local coding sessions or offline development is often unneeded or impossible. To support offline development, secrets-ext detects local override properties:

  • Create a file named application.private.properties or application-sand.private.properties inside your src/main/resources folder.
  • These files are pre-configured in your .gitignore and must never be committed.
  • Write raw, unencrypted override values matching the keys of your target secrets:
# Local raw development secret overrides (src/main/resources/application-sand.private.properties)
encryption.password=myLocalDevRawPasswordValueAndSalt
encryption.salt=4a85da53520247612e50eb0bd5c4ae59
milesoft.apiKey=myLocalDevRawGatewayApiKeyForLocalTesting
milesoft.token=myLocalDevRawGatewayTokenForLocalTesting

At startup, secrets-ext loads these unencrypted local values directly into memory, completely bypassing remote GCP Secret Manager API calls.


5. Integrating with Core Base Configuration Classes

To utilize the core platform features of app-stack, downstream developers extend Spring configuration templates to register Spring-managed beans. Here are three standard configurations generated during the milesoft init process:

5.1 Secrets Configuration (SecretsConfig.java)

Extends the abstract GCP Secret Manager helper, injecting the GCP project identifier to bootstrap the SecretManagerService:

package com.yourcompany.myapp.config;

import io.milesoft.stack.config.AbstractSecretsConfig;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Configuration;

@Configuration
public class SecretsConfig extends AbstractSecretsConfig {

    @Autowired
    public SecretsConfig(@Value("${secrets.project}") String project) {
        super(project);
    }
}

5.2 Accounts Configuration (AccountsConfig.java)

Integrates your application with the central accounts microservice API. It automatically manages API key authentication when invoking platform services:

package com.yourcompany.myapp.config;

import io.milesoft.secrets.services.SecretManagerService;
import io.milesoft.stack.config.AbstractAccountsConfig;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Configuration;

@Configuration
public class AccountsConfig extends AbstractAccountsConfig {

    @Autowired
    public AccountsConfig(
        SecretManagerService secretManagerService,
        @Value("${secrets.milesoft.apiKey}") String secretApiKey,
        @Value("${baseUrl.accounts}") String baseUrl) {

        super(secretManagerService, secretApiKey, baseUrl);
    }
}

5.3 Authentication & Identity Configuration (AuthConfig.java)

Extends the abstract multi-tenant security model. It configures JSON Web Token (JWT) verification, registers an administrative fallback actor context, and establishes token refresh handlers:

package com.yourcompany.myapp.config;

import io.milesoft.accounts.client.v2.AuthClient;
import io.milesoft.app.config.AbstractMultiTenantAuthConfig;
import io.milesoft.app.strategy.RefreshTokenManager;
import io.milesoft.clients.PlatformClient;
import java.time.Clock;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cache.CacheManager;
import org.springframework.context.annotation.Configuration;

@Configuration
public class AuthConfig extends AbstractMultiTenantAuthConfig {

   @Autowired
   public AuthConfig(
           Clock clock,
           PlatformClient platformClient,
           AuthClient authClient,
           CacheManager cacheManager,
           RefreshTokenManager refreshTokenManager,
           @Value("${baseUrl.accounts}") String expectedIssuer,
           @Value("${app.id}") String appId) {

      super(clock, platformClient, authClient, cacheManager, refreshTokenManager, 
              expectedIssuer, appId);
   }
}

6. Compilation & Execution

Once the configuration class extensions are registered and properties files are specified:

  1. Clean and Compile: Clean your workspace and run a compilation phase to ensure all annotation processors (such as Lombok and MapStruct) generate classes successfully:
    ./gradlew clean build -x test
    
  2. Launch locally: Launch the Spring Boot application utilizing your local sandbox environment properties:
    ./gradlew bootRun --args='--spring.profiles.active=sand'
    
  3. Verify Context: Send a GET request to the local actuator endpoint to verify application context health:
    curl http://localhost:8080/actuator/health