Sauron, the all seeing eye!
It is an automated service for tracking backend service migrations, dependency versions, and security vulnerabilities (CVEs). It generates comprehensive reports by analyzing
service changes throughout the deployment lifecycle.
- Sauron Core: Common library shared by all plugins. Details here.
- Sauron Service: The main entry point and orchestrator.
- Plugin System: Extensible architecture (via PF4J) that allows adding logic without restarting the service.
- Storage & Visualization: Uses Elasticsearch for data storage and Kibana for dashboards.
- Dependency-Track: Integrated platform for identifying third-party component risks.
graph LR
%% Inputs
REST[REST API] -.-> SAURON
BUS[Event Bus] -.-> SAURON
subgraph SAURON [Sauron Service]
direction TB
subgraph PIPELINE [Sauron Pipeline]
direction LR
P1[Plugin 1] --> P2[Plugin 2] --> P3[Plugin 3] --> P4[Plugin 4] --> P5[Plugin 5]
end
end
%% Plugin Source
SAURON <==> ARTI[(Artifactory)]
%% Output
PIPELINE --> JSON[JSON Output]
JSON -.-> ES[(Elasticsearch)]
%% Consumers
ES --- GRAFANA[Grafana]
ES --- KIBANA[Kibana]
ES --- ALERTS[Alerts]
%% Styling
style SAURON fill:#f96,stroke:#333,stroke-width:2px
style PIPELINE fill:#fff,stroke:#333,stroke-dasharray: 5 5
style ES fill:#24292e,color:#fff
style ARTI fill:#fff,stroke:#0052cc
Ensure your local environment has the necessary configuration folders (e.g., .m2, .gradle, .pip) as they are mounted as volumes in the Docker containers.
- Build the service:
make
- Start the stack:
This launches:
docker-compose -f docker-compose.yml --compatibility up
- Sauron Service: http://localhost:8080
- Elasticsearch: http://localhost:9200
- Kibana: http://localhost:5601
docker run \
-e SPRING_CONFIG_LOCATION="/sauron/config/sauron-service.yml" \
-e SPRING_PROFILES_INCLUDE="local" \
--mount type=bind,source=${PWD}/docker/config/sauron-service.yml,destination=/sauron/config/sauron-service.yml,readonly \
--mount type=bind,source=${PWD}/plugins,destination=/sauron/plugins \
--mount type=bind,source=${HOME}/.m2,destination=/root/.m2 \
--mount type=bind,source=${HOME}/.gradle,destination=/root/.gradle \
--mount type=bind,source=${HOME}/.pip,destination=/root/.pip \
--mount type=bind,source=${HOME}/.npmrc,destination=/root/.npmrc \
--mount type=bind,source=${HOME}/.ssh,destination=/root/.ssh,readonly \
--name=sauron -p 8080:8080 \
ghcr.io/freenowtech/sauron/sauron-service:latestSettings can be managed via environment variables:
SPRING_CONFIG_LOCATION: Path to your local configuration file (YAML or Properties).SPRING_CLOUD_CONFIG_URI: URL for remote Spring Cloud Config Server.
Refer to sauron-service.yml for a configuration example.
Before triggering builds, apply the index templates:
elasticsearch/sauron-template.sh
elasticsearch/dependencies-template.shUse the REST API to initiate a pipeline run. See Swagger UI for full details.
Example Request:
curl -X POST 'http://localhost:8080/api/v1/build' \
-H 'Content-Type: application/json' \
-d '{
"serviceName": "MyService",
"repositoryUrl": "https://github.com/freenowtech/sauron.git",
"commitId": "latest",
"owner": "Sauron",
"environment": "production"
}'Import the default Kibana Dashboard to view your service data.
Sauron's modularity comes from its plugins. Plugins are reloaded every 5 minutes, or manually via /api/v1/reload.
- console-output: Prints the DataSet to
sysout. - data-sanitizer: Sanitizes data before being processed by Sauron pipeline.
- git-checkout: Clones the source code.
- dependency-checker: Generates CycloneDX SBOMs.
- dependencytrack-publisher: Sends data to Dependency-Track.
- maven-report: Retrieves data from
pom.xmlfile. - elasticsearch-output: Persists results to Elasticsearch.
- protocw-checker: Checks whether a service is using
protoc, andprotoc wrapper. - logs-report: Checks if logs are being produced by a service.
- kubernetesapi-report: Retrieves annotations and labels assigned to a resource.
- sonarapi-report: Retrieves service related data as Code Coverage.
- thanosapi-report: Retrieves service related data as RPM and Circuit Breaker metrics.
- readme-report: Checks whether a service has a README.md file in its root folder.
- cleanup: Purges the workspace after the pipeline finishes.
- Install the archetype:
cd sauron-plugin-archetype mvn clean install - Generate the skeleton:
mvn archetype:generate -DarchetypeArtifactId=sauron-plugin-archetype
- Implement logic: Override the apply method in your generated class.
package com.freenow.sauron.plugins; import com.freenow.sauron.model.DataSet; import com.freenow.sauron.properties.PluginsConfigurationProperties; import org.pf4j.Extension; @Extension public class MyPlugin implements SauronExtension { @Override public DataSet apply(PluginsConfigurationProperties properties, DataSet input) { // @TODO: Your magic here return input; } }
- Plugin configuration: To provide extra configuration to the plugin, add your configuration to the service configurations and it will be available at
PluginsConfigurationProperties.sauron: plugins: my-plugin: url: https://my-plugin.com
@Extension public class MyPlugin implements SauronExtension { @Override public DataSet apply(PluginsConfigurationProperties properties, DataSet input) { properties.getPluginConfigurationProperty("my-plugin", "url").ifPresent(url -> System.out.println(url) ); return input; } }
- Deploy: Add your JAR to the configured plugin repository (Local or Artifactory).
