feat: add Phase 3 dependencies and configuration

Add docker-java and ClickHouse JDBC dependencies, RuntimeConfig and
ClickHouseConfig Spring components, AsyncConfig with deployment thread
pool, and runtime/clickhouse config sections in application.yml.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
hsiegeln
2026-04-04 17:29:06 +02:00
parent c0fce36d4a
commit 803b8c9876
5 changed files with 150 additions and 0 deletions

20
pom.xml
View File

@@ -80,6 +80,26 @@
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
<!-- Docker Java client -->
<dependency>
<groupId>com.github.docker-java</groupId>
<artifactId>docker-java-core</artifactId>
<version>3.4.1</version>
</dependency>
<dependency>
<groupId>com.github.docker-java</groupId>
<artifactId>docker-java-transport-httpclient5</artifactId>
<version>3.4.1</version>
</dependency>
<!-- ClickHouse JDBC -->
<dependency>
<groupId>com.clickhouse</groupId>
<artifactId>clickhouse-jdbc</artifactId>
<version>0.7.1</version>
<classifier>all</classifier>
</dependency>
<!-- Test -->
<dependency>
<groupId>org.springframework.boot</groupId>

View File

@@ -0,0 +1,31 @@
package net.siegeln.cameleer.saas.config;
import net.siegeln.cameleer.saas.runtime.RuntimeConfig;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.scheduling.annotation.EnableAsync;
import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;
import java.util.concurrent.Executor;
@Configuration
@EnableAsync
public class AsyncConfig {
private final RuntimeConfig runtimeConfig;
public AsyncConfig(RuntimeConfig runtimeConfig) {
this.runtimeConfig = runtimeConfig;
}
@Bean(name = "deploymentExecutor")
public Executor deploymentExecutor() {
var executor = new ThreadPoolTaskExecutor();
executor.setCorePoolSize(runtimeConfig.getDeploymentThreadPoolSize());
executor.setMaxPoolSize(runtimeConfig.getDeploymentThreadPoolSize());
executor.setQueueCapacity(25);
executor.setThreadNamePrefix("deploy-");
executor.initialize();
return executor;
}
}

View File

@@ -0,0 +1,22 @@
package net.siegeln.cameleer.saas.log;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import javax.sql.DataSource;
import com.clickhouse.jdbc.ClickHouseDataSource;
import java.util.Properties;
@Configuration
public class ClickHouseConfig {
@Value("${cameleer.clickhouse.url:jdbc:clickhouse://clickhouse:8123/cameleer}")
private String url;
@Bean(name = "clickHouseDataSource")
public DataSource clickHouseDataSource() throws Exception {
var properties = new Properties();
return new ClickHouseDataSource(url, properties);
}
}

View File

@@ -0,0 +1,63 @@
package net.siegeln.cameleer.saas.runtime;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;
@Component
public class RuntimeConfig {
@Value("${cameleer.runtime.max-jar-size:209715200}")
private long maxJarSize;
@Value("${cameleer.runtime.jar-storage-path:/data/jars}")
private String jarStoragePath;
@Value("${cameleer.runtime.base-image:cameleer-runtime-base:latest}")
private String baseImage;
@Value("${cameleer.runtime.docker-network:cameleer}")
private String dockerNetwork;
@Value("${cameleer.runtime.agent-health-port:9464}")
private int agentHealthPort;
@Value("${cameleer.runtime.health-check-timeout:60}")
private int healthCheckTimeout;
@Value("${cameleer.runtime.deployment-thread-pool-size:4}")
private int deploymentThreadPoolSize;
@Value("${cameleer.runtime.container-memory-limit:512m}")
private String containerMemoryLimit;
@Value("${cameleer.runtime.container-cpu-shares:512}")
private int containerCpuShares;
@Value("${cameleer.runtime.bootstrap-token:${CAMELEER_AUTH_TOKEN:}}")
private String bootstrapToken;
@Value("${cameleer.runtime.cameleer3-server-endpoint:http://cameleer3-server:8081}")
private String cameleer3ServerEndpoint;
public long getMaxJarSize() { return maxJarSize; }
public String getJarStoragePath() { return jarStoragePath; }
public String getBaseImage() { return baseImage; }
public String getDockerNetwork() { return dockerNetwork; }
public int getAgentHealthPort() { return agentHealthPort; }
public int getHealthCheckTimeout() { return healthCheckTimeout; }
public int getDeploymentThreadPoolSize() { return deploymentThreadPoolSize; }
public String getContainerMemoryLimit() { return containerMemoryLimit; }
public int getContainerCpuShares() { return containerCpuShares; }
public String getBootstrapToken() { return bootstrapToken; }
public String getCameleer3ServerEndpoint() { return cameleer3ServerEndpoint; }
public long parseMemoryLimitBytes() {
var limit = containerMemoryLimit.trim().toLowerCase();
if (limit.endsWith("g")) {
return Long.parseLong(limit.substring(0, limit.length() - 1)) * 1024 * 1024 * 1024;
} else if (limit.endsWith("m")) {
return Long.parseLong(limit.substring(0, limit.length() - 1)) * 1024 * 1024;
}
return Long.parseLong(limit);
}
}

View File

@@ -33,3 +33,17 @@ cameleer:
logto-endpoint: ${LOGTO_ENDPOINT:}
m2m-client-id: ${LOGTO_M2M_CLIENT_ID:}
m2m-client-secret: ${LOGTO_M2M_CLIENT_SECRET:}
runtime:
max-jar-size: 209715200
jar-storage-path: ${CAMELEER_JAR_STORAGE_PATH:/data/jars}
base-image: ${CAMELEER_RUNTIME_BASE_IMAGE:cameleer-runtime-base:latest}
docker-network: ${CAMELEER_DOCKER_NETWORK:cameleer}
agent-health-port: 9464
health-check-timeout: 60
deployment-thread-pool-size: 4
container-memory-limit: ${CAMELEER_CONTAINER_MEMORY_LIMIT:512m}
container-cpu-shares: ${CAMELEER_CONTAINER_CPU_SHARES:512}
bootstrap-token: ${CAMELEER_AUTH_TOKEN:}
cameleer3-server-endpoint: ${CAMELEER3_SERVER_ENDPOINT:http://cameleer3-server:8081}
clickhouse:
url: ${CLICKHOUSE_URL:jdbc:clickhouse://clickhouse:8123/cameleer}