Skip to content

Component

A Component is a building block of a service in Odin. Components represent individual pieces of infrastructure or application logic that work together to form a complete service.

Components are the fundamental deployment units in Odin. They can represent:

  • Web Services: API servers, web applications, microservices
  • Databases: PostgreSQL, MySQL, MongoDB
  • Caches: Redis, Memcached
  • Message Queues: RabbitMQ, Kafka, SQS
  • Storage: S3 buckets, file systems
  • Any other infrastructure: Load balancers, DNS records, etc.

Components are defined within a service definition:

{
"name": "api-server",
"type": "webservice",
"version": "2.1.0",
"depends_on": ["database", "cache"],
"config": {
"port": 8080,
"replicas": 3,
"env": {
"LOG_LEVEL": "info"
}
}
}
PropertyRequiredDescription
nameYesUnique identifier within the service
typeYesComponent type (registered in Odin)
versionYesComponent version
depends_onNoArray of component names this depends on
configNoComponent-specific configuration (JSON object)

Components have types that determine how they’re deployed and managed. Common types include:

  • webservice: HTTP/gRPC services
  • postgres: PostgreSQL database
  • mysql: MySQL database
  • redis: Redis cache
  • mongodb: MongoDB database
  • rabbitmq: RabbitMQ message broker
  • kafka: Apache Kafka
  • s3: S3 bucket
  • lambda: AWS Lambda function

Components can depend on other components. Odin uses these dependencies to:

  1. Determine deployment order: Deploy dependencies first
  2. Validate configurations: Ensure all dependencies exist
  3. Prevent unsafe operations: Can’t remove a component if others depend on it

Use the depends_on field to specify dependencies:

{
"components": [
{
"name": "api",
"depends_on": ["database", "cache", "queue"]
},
{
"name": "worker",
"depends_on": ["database", "queue"]
},
{
"name": "database",
"depends_on": []
},
{
"name": "cache",
"depends_on": []
},
{
"name": "queue",
"depends_on": []
}
]
}

Deployment Order:

  1. database, cache, queue (parallel, no dependencies)
  2. api, worker (parallel, after dependencies are ready)

Odin automatically creates a dependency graph and deploys in topologically sorted order:

database ──┐
├──> api
cache ─────┤
queue ─────┼──> worker

Components transition through several states:

StateDescription
DEPLOYINGComponent is being deployed
DEPLOYEDComponent successfully deployed
FAILEDDeployment failed
UPDATINGComponent is being updated
UNDEPLOYINGComponent is being removed
UNDEPLOYEDComponent has been removed

Check component status within a service:

Terminal window
odin status env staging --service my-service

Get detailed information about a specific component:

Terminal window
odin describe env staging --service my-service --component database

Execute operations on individual components:

Terminal window
odin operate component --name <component-name> \
--service <service-name> \
--env <env-name> \
--operation <operation-type> \
--options '{"key": "value"}'

Or use a file:

Terminal window
odin operate component --name <component-name> \
--service <service-name> \
--env <env-name> \
--operation <operation-type> \
--file operation.json

Scale up/down replicas:

Terminal window
odin operate component --name api \
--service user-api \
--env production \
--operation scale \
--options '{"replicas": 5}'

Restart a component (rolling restart):

Terminal window
odin operate component --name api \
--service user-api \
--env staging \
--operation restart

Update component configuration:

Terminal window
odin operate component --name api \
--service user-api \
--env staging \
--operation update-config \
--options '{
"env": {
"LOG_LEVEL": "debug",
"CACHE_TTL": "3600"
}
}'

Add a new component to an existing service:

Terminal window
odin operate service --name user-api \
--env staging \
--operation ADD_COMPONENT \
--file add-component.json

add-component.json:

{
"component_definition": {
"name": "new-cache",
"type": "redis",
"version": "7.0",
"config": {
"memory": "4Gi"
}
},
"provisioning_config": {
"component_name": "new-cache",
"deployment_type": "elasticache-redis",
"params": {
"node_type": "cache.t3.medium",
"num_nodes": 2
}
}
}

Remove a component from a service:

Terminal window
odin operate service --name user-api \
--env staging \
--operation REMOVE_COMPONENT \
--options '{"component_name": "old-cache"}'

Safety Checks:

  • Component must exist in the service
  • Component must be in a terminal state (DEPLOYED or FAILED)
  • No other components can depend on it

Components have a flexible config field for component-specific settings:

{
"name": "api",
"type": "webservice",
"config": {
"port": 8080,
"replicas": 3,
"cpu": "500m",
"memory": "1Gi",
"env": {
"LOG_LEVEL": "info",
"DB_HOST": "database:5432",
"CACHE_URL": "redis://cache:6379"
},
"healthcheck": {
"path": "/health",
"interval": 30
}
}
}
{
"name": "database",
"type": "postgres",
"config": {
"storage": "100Gi",
"instance_class": "db.r5.large",
"multi_az": true,
"backup_retention_days": 7,
"parameters": {
"max_connections": "200",
"shared_buffers": "256MB"
}
}
}
{
"name": "cache",
"type": "redis",
"config": {
"memory": "4Gi",
"eviction_policy": "allkeys-lru",
"persistence": false,
"replicas": 2
}
}

Each component needs provisioning configuration that specifies how and where it’s deployed. See Provisioning for details.

Use clear, descriptive names:

  • api, web, server: For web services
  • database, db, postgres: For databases
  • cache, redis: For caches
  • queue, mq, broker: For message queues
  1. Minimal Dependencies: Only depend on what you actually need
  2. Order Matters: List dependencies in the order they’re needed
  3. Avoid Cycles: Circular dependencies are not allowed
  1. Environment Variables: Use env for configuration that changes between environments
  2. Defaults: Provide sensible defaults in the service definition
  3. Secrets: Don’t put secrets in the service definition; use provisioning configs
  4. Resource Limits: Always specify CPU and memory limits
  1. Pin Versions: Always specify exact component versions
  2. Test Upgrades: Test component version upgrades in staging first
  3. Compatibility: Ensure component versions are compatible with each other
{
"name": "api",
"type": "webservice",
"version": "1.0.0",
"config": {
"port": 8080,
"replicas": 2
}
}
{
"name": "main-db",
"type": "postgres",
"version": "14.5",
"config": {
"storage": "200Gi",
"instance_class": "db.r5.xlarge",
"multi_az": true,
"backup_retention_days": 14,
"backup_window": "03:00-04:00",
"maintenance_window": "sun:04:00-sun:05:00"
}
}
{
"name": "cache-cluster",
"type": "redis",
"version": "7.0",
"config": {
"memory": "8Gi",
"replicas": 3,
"persistence": true,
"eviction_policy": "volatile-lru",
"parameters": {
"maxmemory-policy": "volatile-lru",
"timeout": "300"
}
}
}