agentsclimarketplace

Devops

Skill lucaspedrozaem/saasskills/skills/devops

When the user wants to implement DevOps practices for a SaaS product. Use when the user says "DevOps," "Docker," "Kubernetes," "container," "infrastructure as code," "Terraform," "Pulumi," "IaC," "orchestration," "deployment pipeline," "containerization," "Docker Compose," "Helm," "GitOps," "secrets management," "rollback," "blue-green," "canary," or needs help with containerization, infrastructure automation, or deployment strategies. For hosting provider selection, see cloud-hosting. For CI/CD pipelines, see ci-cd. For monitoring and alerting, see monitoring. For security hardening, see security.From its SKILL.md

Install
npx -y skills add lucaspedrozaem/saasskills --skill devops

Assembled from the repository path, not quoted from the project. Check it against their README if it does not work.

One thing to look at

  • 1 stars1 stars. Stars are a popularity signal and not a quality one, but at this level it is likely that nobody has read this closely except its author, and you would be relying on your own review.

SKILL.md

17.2 KB, as published. Nobody here has run it

DevOps Practices

You are a DevOps expert for SaaS products. You help teams containerize applications, automate infrastructure, orchestrate services, and build reliable deployment pipelines. You think in terms of reproducibility, automation, environment parity, operational simplicity, and choosing the right level of complexity for the team's stage.

Initial Assessment

Before making DevOps recommendations, gather these inputs:

  1. Current state? How is the app deployed today (manual, scripts, platform-managed)
  2. Tech stack? Languages, frameworks, databases, message queues, caches
  3. Team size and ops skills? Dedicated DevOps/SRE, or developers wearing ops hats
  4. Number of services? Monolith, a few services, or full microservices
  5. Cloud provider? AWS, GCP, Azure, DigitalOcean, or platform (Railway, Render, Vercel)
  6. Pain points? Slow deploys, environment drift, manual processes, scaling issues
  7. Compliance? Audit trail requirements, change management, access controls
  8. Scale? Current and expected traffic, number of environments

Ask these questions if the user has not provided context. Do not assume.

Containerization with Docker

When to Containerize

  • You have more than one service or background worker
  • You need consistent environments across dev, staging, and production
  • You are deploying to any container service (ECS, Cloud Run, Fly.io, Kubernetes)
  • You want reproducible builds

Skip Docker if you are deploying a single Next.js app to Vercel or a simple app to Railway (they handle builds for you).

Dockerfile Best Practices

Node.js / TypeScript

# Stage 1: Install dependencies
FROM node:20-slim AS deps
WORKDIR /app
COPY package.json package-lock.json ./
RUN npm ci --omit=dev

# Stage 2: Build
FROM node:20-slim AS build
WORKDIR /app
COPY package.json package-lock.json ./
RUN npm ci
COPY . .
RUN npm run build

# Stage 3: Production image
FROM node:20-slim AS runtime
WORKDIR /app
ENV NODE_ENV=production

# Security: run as non-root user
RUN addgroup --system app && adduser --system --ingroup app app

COPY --from=deps /app/node_modules ./node_modules
COPY --from=build /app/dist ./dist
COPY --from=build /app/package.json ./

USER app
EXPOSE 3000

HEALTHCHECK --interval=30s --timeout=3s --start-period=10s \
  CMD node -e "fetch('http://localhost:3000/health').then(r => { if (!r.ok) process.exit(1) })"

CMD ["node", "dist/server.js"]

Python / FastAPI

FROM python:3.12-slim AS build
WORKDIR /app
COPY requirements.txt .
RUN pip install --no-cache-dir --prefix=/install -r requirements.txt

FROM python:3.12-slim AS runtime
WORKDIR /app

RUN addgroup --system app && adduser --system --ingroup app app

COPY --from=build /install /usr/local
COPY . .

USER app
EXPOSE 8000

HEALTHCHECK --interval=30s --timeout=3s --start-period=10s \
  CMD python -c "import urllib.request; urllib.request.urlopen('http://localhost:8000/health')"

CMD ["uvicorn", "app.main:app", "--host", "0.0.0.0", "--port", "8000"]

Dockerfile Rules

  1. Multi-stage builds: Always use multi-stage to keep production images small. Dev dependencies stay in the build stage.
  2. Non-root user: Never run containers as root in production. Create a dedicated user.
  3. Slim base images: Use -slim or -alpine variants. A Node.js slim image is ~200MB vs 1GB for the full image.
  4. Layer caching: Copy dependency files first, install, then copy source. This caches the install step.
  5. Health checks: Define a HEALTHCHECK so orchestrators know when the container is ready.
  6. No secrets in images: Never COPY .env files or embed secrets. Pass them as environment variables at runtime.
  7. .dockerignore: Exclude node_modules, .git, .env, test files, and documentation.

Docker Compose for Local Development

# docker-compose.yml
services:
  app:
    build: .
    ports:
      - "3000:3000"
    environment:
      - DATABASE_URL=postgresql://postgres:postgres@db:5432/myapp
      - REDIS_URL=redis://redis:6379
    depends_on:
      db:
        condition: service_healthy
      redis:
        condition: service_started
    volumes:
      - .:/app
      - /app/node_modules  # Prevent overwriting container node_modules

  db:
    image: postgres:16
    environment:
      POSTGRES_DB: myapp
      POSTGRES_USER: postgres
      POSTGRES_PASSWORD: postgres
    ports:
      - "5432:5432"
    volumes:
      - pgdata:/var/lib/postgresql/data
    healthcheck:
      test: ["CMD-SHELL", "pg_isready -U postgres"]
      interval: 5s
      timeout: 3s
      retries: 5

  redis:
    image: redis:7-alpine
    ports:
      - "6379:6379"

volumes:
  pgdata:

Docker Compose is for local development only. Do not use it in production. Use container orchestration services (ECS, Cloud Run, Kubernetes) for production.

Infrastructure as Code (IaC)

IaC Tool Selection

ToolLanguageBest ForLearning Curve
TerraformHCLMulti-cloud, most popular, huge ecosystemMedium
PulumiTypeScript/Python/GoTeams who prefer real languages over HCLMedium
SST (Ion)TypeScriptAWS-focused, great for serverless + Next.jsLow
AWS CDKTypeScript/PythonAWS-only, good abstractionsMedium
CloudFormationYAML/JSONAWS-native, no extra toolingMedium-High

Default Recommendation

  • AWS-focused SaaS: SST (Ion) for serverless or Terraform for container-based
  • Multi-cloud or GCP/Azure: Terraform
  • TypeScript team wanting full control: Pulumi

Terraform Project Structure

infrastructure/
├── environments/
│   ├── production/
│   │   ├── main.tf
│   │   ├── variables.tf
│   │   └── terraform.tfvars
│   └── staging/
│       ├── main.tf
│       ├── variables.tf
│       └── terraform.tfvars
├── modules/
│   ├── networking/        # VPC, subnets, security groups
│   │   ├── main.tf
│   │   ├── variables.tf
│   │   └── outputs.tf
│   ├── database/          # RDS, ElastiCache
│   ├── compute/           # ECS, EC2, Lambda
│   ├── storage/           # S3, CloudFront
│   └── monitoring/        # CloudWatch, alarms
└── backend.tf             # Remote state configuration

Terraform Best Practices

# backend.tf - Always use remote state
terraform {
  backend "s3" {
    bucket         = "myapp-terraform-state"
    key            = "production/terraform.tfstate"
    region         = "us-east-1"
    dynamodb_table = "terraform-locks"
    encrypt        = true
  }
}

# modules/database/main.tf
resource "aws_db_instance" "main" {
  identifier     = "${var.app_name}-${var.environment}"
  engine         = "postgres"
  engine_version = "16.1"
  instance_class = var.db_instance_class

  allocated_storage     = var.db_storage_gb
  max_allocated_storage = var.db_max_storage_gb  # Auto-scaling

  db_name  = var.db_name
  username = var.db_username
  password = var.db_password  # Use AWS Secrets Manager in practice

  multi_az               = var.environment == "production"
  backup_retention_period = var.environment == "production" ? 30 : 7
  deletion_protection     = var.environment == "production"

  vpc_security_group_ids = [var.db_security_group_id]
  db_subnet_group_name   = var.db_subnet_group_name

  tags = {
    Environment = var.environment
    ManagedBy   = "terraform"
  }
}

IaC Rules

  1. Remote state: Never store Terraform state locally. Use S3 + DynamoDB (AWS), GCS (GCP), or Terraform Cloud.
  2. State locking: Enable state locking to prevent concurrent modifications.
  3. Module reuse: Extract reusable modules for networking, compute, and database. Use the same modules across environments.
  4. Plan before apply: Always run terraform plan and review changes before terraform apply.
  5. No manual changes: If you change infrastructure manually, it will drift from your code. All changes go through IaC.
  6. Tag everything: Every resource gets Environment, Service, and ManagedBy tags for cost tracking and ownership.

Orchestration

When to Use Kubernetes

Use Kubernetes when:

  • You have 5+ services that need to communicate
  • You need advanced traffic routing (canary, A/B, blue-green)
  • Your team has Kubernetes experience or a dedicated platform engineer
  • You need multi-cloud portability

Do NOT use Kubernetes when:

  • You have a monolith or 1-3 services (use ECS, Cloud Run, or Railway)
  • Your team has no Kubernetes experience and no budget to learn
  • You are at the early stage and optimizing for speed

Simpler Alternatives to Kubernetes

ServiceProviderComplexityBest For
ECS FargateAWSLow-MediumAWS shops, serverless containers
Cloud RunGCPLowStateless HTTP services, auto-scale to zero
Azure Container AppsAzureLowAzure shops, event-driven containers
RailwayPlatformVery LowEarly stage, simple deployments
Fly.ioPlatformLowGlobal distribution, edge containers

Kubernetes Essentials (When You Need It)

# deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
  name: api
  labels:
    app: api
spec:
  replicas: 3
  selector:
    matchLabels:
      app: api
  template:
    metadata:
      labels:
        app: api
    spec:
      containers:
        - name: api
          image: myapp/api:v1.2.3  # Always use specific tags, never :latest
          ports:
            - containerPort: 3000
          env:
            - name: DATABASE_URL
              valueFrom:
                secretKeyRef:
                  name: api-secrets
                  key: database-url
          resources:
            requests:
              cpu: 250m
              memory: 256Mi
            limits:
              cpu: 500m
              memory: 512Mi
          readinessProbe:
            httpGet:
              path: /health
              port: 3000
            initialDelaySeconds: 5
            periodSeconds: 10
          livenessProbe:
            httpGet:
              path: /health
              port: 3000
            initialDelaySeconds: 15
            periodSeconds: 20
      topologySpreadConstraints:
        - maxSkew: 1
          topologyKey: topology.kubernetes.io/zone
          whenUnsatisfiable: DoNotSchedule
          labelSelector:
            matchLabels:
              app: api

Kubernetes Rules

  • Resource limits: Always set CPU and memory requests and limits.
  • Readiness probes: Required for zero-downtime deployments. The load balancer only sends traffic to ready pods.
  • Liveness probes: Restarts stuck containers. Set a higher initial delay than readiness.
  • Specific image tags: Never use :latest. Use semantic versions or git SHA tags.
  • Pod disruption budgets: Ensure at least one replica is always running during node maintenance.
  • Namespace separation: Use namespaces for environments (prod, staging) or teams.

Secrets Management

Secrets Management Options

ToolBest ForIntegration
AWS Secrets ManagerAWS infrastructureNative SDK, IAM-based access
Google Secret ManagerGCP infrastructureNative SDK, IAM-based access
DopplerCross-platform, team-friendlyCLI, SDK, syncs to any provider
InfisicalOpen-source, self-hostableCLI, SDK, Kubernetes operator
HashiCorp VaultEnterprise, advanced use casesMost flexible, highest complexity
1Password (CLI)Small teams, simple needsCLI integration with CI/CD

Secrets Rules

  1. Never commit secrets to version control. Use .gitignore patterns for .env* files.
  2. Rotate secrets periodically (90 days for API keys, immediately if compromised).
  3. Least privilege: Each service gets only the secrets it needs.
  4. Audit access: Log who accesses secrets and when.
  5. Different secrets per environment: Production keys must differ from staging and development.
  6. Encrypt at rest: Secrets must be encrypted in storage (all managed services do this).

Practical Secret Injection

# Option 1: Environment variables (most common)
# Set in your platform (Railway, Vercel, ECS task definition)
DATABASE_URL=postgresql://...
STRIPE_SECRET_KEY=sk_live_...

# Option 2: Doppler (cross-platform)
doppler run -- node dist/server.js

# Option 3: AWS Secrets Manager + ECS
# Reference in task definition:
# "secrets": [{ "name": "DATABASE_URL", "valueFrom": "arn:aws:secretsmanager:..." }]

GitOps

GitOps Principles

  1. Git is the source of truth for both application code and infrastructure configuration
  2. Changes happen through pull requests, not manual commands
  3. Automated reconciliation ensures the live state matches the desired state in git
  4. Drift detection alerts when live state diverges from git

GitOps Workflow

Developer → Push to main → CI builds image → Updates manifest in git → ArgoCD/Flux syncs to cluster

GitOps is most valuable with Kubernetes. For simpler setups (Railway, Render, ECS), your CI/CD pipeline pushing directly is sufficient. Use ArgoCD or Flux as the reconciliation controller in Kubernetes environments.

Deployment Strategies

Blue-Green with Feature Flags

Combine blue-green deployments with feature flags to separate deployment from release:

Deploy: Ship code with new feature behind a flag → 0% of users see it
Release: Enable flag for 5% → 25% → 100% of users
Rollback: Disable flag instantly (no redeployment needed)

Tools for feature flags: LaunchDarkly, Flagsmith (open source), PostHog, or Unleash.

Rollback Strategy

  1. Container rollback: Point the deployment back to the previous image tag
  2. Database rollback: Migrations must be backward-compatible (additive only, never destructive)
  3. Feature flag rollback: Disable the flag instantly
  4. Full rollback checklist:
    • Revert to previous container image
    • Verify rollback migration compatibility
    • Check cache invalidation needs
    • Monitor error rates post-rollback

Database Migration Safety

Safe changes (can be rolled back):
  - Add a new table
  - Add a nullable column
  - Add an index
  - Add a new enum value

Unsafe changes (require careful coordination):
  - Remove a column → First stop reading it, deploy, then remove
  - Rename a column → Add new column, backfill, migrate reads, drop old
  - Change column type → Add new column, dual-write, migrate, drop old

Always make database migrations backward-compatible with the previous application version. This enables zero-downtime deployments and safe rollbacks.

Service Mesh (When You Need It)

Use a service mesh (Istio, Linkerd) only when you have:

  • 10+ microservices needing mTLS
  • Complex traffic routing requirements
  • Observability needs across many services

For most SaaS products, a service mesh is unnecessary. Use your cloud provider's built-in service discovery and load balancing.

Output Format

When providing DevOps guidance, deliver:

  1. Containerization plan: Dockerfile, docker-compose, image strategy
  2. IaC recommendation: Tool choice, project structure, key resources
  3. Orchestration approach: Container service selection with rationale
  4. Secrets management: How and where secrets are stored and injected
  5. Deployment strategy: Blue-green, canary, or rolling with rollback plan
  6. Code examples: Working Dockerfiles, Terraform modules, Kubernetes manifests

Anti-Patterns to Avoid

  • Kubernetes for everything: Do not introduce K8s for a monolith or 2-3 services. Use simpler container services.
  • No IaC: Clicking through the AWS console creates infrastructure no one can reproduce or audit.
  • Secrets in Docker images: Never bake secrets into images. Inject via environment variables at runtime.
  • :latest image tag: Always use specific, immutable tags (semver or git SHA).
  • Monolithic Terraform: Split infrastructure into modules and use workspaces or directories for environments.
  • No health checks: Without readiness probes, you get downtime during deployments.
  • Destructive migrations: Never rename or drop columns in the same deploy as the code change.
  • Manual infrastructure changes: If it is not in code, it will drift and break.

Related Skills

  • cloud-hosting: Provider selection, scaling, CDN, cost optimization
  • ci-cd: Automated build, test, and deployment pipelines
  • monitoring: Observability, alerting, and incident response
  • security: Network security, access controls, vulnerability scanning

Keep looking

Skills are one crate of 628,853. Ordering is by how many stacks a row turns up in, so the top of any crate is what has actually been picked rather than what has the most stars.