This application exposes the SDKMAN Candidate and Version state through a JSON API.
It exposes GET, POST, PATCH and DELETE HTTP methods on candidates and versions.
The audience of this API is twofold:
- as a backend for the native components written in Rust
- as admin API of the datastore, used directly or by build system plugins and the DISCO integration
-
Start PostgreSQL database:
docker run --restart=always \ --name postgres \ -p 5432:5432 \ -e POSTGRES_USER=postgres \ -e POSTGRES_PASSWORD=postgres \ -e POSTGRES_DB=sdkman \ -d postgres -
Run the service:
./gradlew run
The service will start on port 8080.
./gradlew testhttp POST localhost:8080/versions \
candidate=java \
version=21.0.2 \
platform=LINUX_X64 \
url=https://download.oracle.com/java/21/archive/jdk-21.0.1_linux-x64_bin.tar.gz \
visible:=true \
--auth testuser:password123http GET localhost:8080/versions/javaThe audit table tracks download and usage events for SDKMAN candidates. The following indexes optimize common analytical queries:
SELECT COUNT(*) as downloads
FROM audit
WHERE candidate = 'java'
AND timestamp > NOW() - INTERVAL '30 days';Uses index: idx_audit_candidate_timestamp
SELECT version, COUNT(*) as downloads
FROM audit
WHERE candidate = 'gradle'
GROUP BY version
ORDER BY downloads DESC
LIMIT 10;Uses index: idx_audit_candidate_version_timestamp
SELECT version,
DATE_TRUNC('week', timestamp) as week,
COUNT(*) as downloads
FROM audit
WHERE candidate = 'kotlin'
AND timestamp > NOW() - INTERVAL '6 months'
GROUP BY version, week
ORDER BY week DESC, downloads DESC;Uses index: idx_audit_candidate_version_timestamp
SELECT command, COUNT(*) as count
FROM audit
WHERE candidate = 'java'
AND timestamp > NOW() - INTERVAL '90 days'
GROUP BY command
ORDER BY count DESC;Uses index: idx_audit_candidate_command_timestamp
SELECT candidate,
COUNT(*) as events,
MAX(timestamp) as last_activity
FROM audit
WHERE timestamp > NOW() - INTERVAL '7 days'
GROUP BY candidate
ORDER BY events DESC;Uses index: idx_audit_timestamp_candidate
SELECT platform,
COUNT(*) as downloads,
ROUND(COUNT(*) * 100.0 / SUM(COUNT(*)) OVER (), 2) as percentage
FROM audit
WHERE candidate = 'kotlin'
AND timestamp > NOW() - INTERVAL '90 days'
GROUP BY platform
ORDER BY downloads DESC;Uses index: idx_audit_candidate_platform_timestamp
SELECT vendor,
platform,
COUNT(*) as downloads,
COUNT(DISTINCT DATE_TRUNC('day', timestamp)) as days_active
FROM audit
WHERE candidate = 'java'
AND platform = 'LINUX_X64'
AND vendor IS NOT NULL
AND timestamp > NOW() - INTERVAL '6 months'
GROUP BY vendor, platform
ORDER BY downloads DESC;Uses index: idx_audit_candidate_platform_vendor_timestamp
SELECT host,
COUNT(*) as activity_count,
COUNT(DISTINCT candidate) as unique_candidates,
MAX(timestamp) as last_seen
FROM audit
WHERE timestamp > NOW() - INTERVAL '30 days'
AND host IS NOT NULL
GROUP BY host
ORDER BY activity_count DESC
LIMIT 20;SELECT EXTRACT(HOUR FROM timestamp) as hour,
COUNT(*) as events
FROM audit
WHERE timestamp > NOW() - INTERVAL '7 days'
GROUP BY hour
ORDER BY hour;Uses index: idx_audit_timestamp_candidate