Back to articles
Technology Insight

Deploying Kamal 2 on Cloud VPS: How Basecamp Deploys Production Apps Without Kubernetes

June 2, 2026

Introduction: The Shift Away from Container Orchestration Complexity

For nearly a decade, the tech industry has treated Kubernetes (K8s) and Docker Swarm as the default answers for deploying containerized applications to production. While these orchestration platforms offer unparalleled scaling capabilities for massive enterprises, they introduce a mountain of complexity, steep learning curves, and significant infrastructure overhead for small-to-medium businesses and independent SaaS builders.

Enter Kamal 2 (formerly known as MRSK), an open-source deployment tool created by David Heinemeier Hansson (DHH) and the team at 37signals (Basecamp & HEY). Kamal 2 represents a philosophical pivot back to simplicity: deploying production-grade, containerized applications directly to standard Cloud VPS (Virtual Private Servers) without the need for an orchestration layer. This guide explores how Kamal 2 achieves this, its underlying architecture, and a step-by-step framework for deploying your applications to production.

Why Basecamp Rejected Kubernetes for Kamal 2

To understand why Kamal 2 exists, one must look at Basecamp's famous cloud exit. In 2023, 37signals moved their applications out of major cloud providers to bare-metal servers and standard VPS instances, saving millions of dollars annually. During this transition, they sought a deployment experience that matched the ease of platforms-as-a-service (PaaS) like Heroku, but with the control and cost efficiency of self-hosting.

They discovered that Kubernetes introduced unnecessary abstractions. For a typical application consisting of a web server, a database, and a background worker, K8s requires managing Pods, Deployments, Services, Ingress Controllers, and Persistent Volume Claims. Kamal 2 strips all of this away. It utilizes plain Docker and SSH, treating servers as predictable, bare targets. It proves that you do not need complex orchestration to achieve modern deployment requirements such as zero-downtime rollouts, asset caching, and automated SSL termination.

The Architecture of Kamal 2

Kamal 2 is fundamentally a CLI tool written in Ruby, but it can deploy applications written in any language or framework (Node.js, Python, Go, Rust, Ruby on Rails) as long as the application can be packaged into a Docker image. It operates via standard SSH connections from your local machine or a CI/CD pipeline (like GitHub Actions) to your target VPS.

Key Components of Kamal 2:

  • The Kamal Proxy: Replaces the old Traefik setup from Kamal 1. It is a lightweight, high-performance web proxy built specifically for Kamal 2. It handles incoming traffic, routes requests to the active container, and facilitates seamless zero-downtime switching during deployments.
  • Automatic SSL via Let's Encrypt: Kamal 2 integrates native provision for Let's Encrypt certificates directly inside the Kamal Proxy, eliminating the need to configure separate certificate managers.
  • Docker & SSH: Kamal connects over SSH, builds or pulls your Docker image, boots the new container, verifies its health, switches the proxy route, and stops the old container.

Prerequisites for Deployment

Before initiating a Kamal 2 deployment, ensure you have the following components prepared:

  1. One or more Cloud VPS instances: A clean installation of Ubuntu 22.04 or 24.04 LTS on a provider like DigitalOcean, Linode, Hetzner, or AWS EC2. SSH key access must be configured.
  2. Docker Hub or a private Container Registry: GitHub Packages (GHCR), GitLab Registry, or AWS ECR to host your application images.
  3. A Domain Name: Pointing via A/AAAA records to your primary VPS public IP address.
  4. Local Environment Setup: Docker and Ruby installed locally (or run Kamal via its official Docker image container to avoid local dependencies).

Step-by-Step Implementation Guide

Step 1: Initialize Kamal in Your Project

Navigate to your application's root directory and run the initialization command. This generates the core configuration files needed to manage your infrastructure:

kamal init

This command creates a config/deploy.yml file for configuration parameters and a .env file for storing sensitive credentials like registry passwords and database tokens.

Step 2: Configuring the deploy.yml File

The config/deploy.yml file is the single source of truth for your deployment. Here is an optimized production configuration template for Kamal 2:


service: my-core-app
image: username/my-core-app

servers:
  web:
    - 192.168.1.100

proxy:
  ssl: true
  host: app.yourdomain.com
  app_port: 3000

registry:
  username: my-docker-username
  password:
    - KAMAL_REGISTRY_PASSWORD

env:
  clear:
    NODE_ENV: production
  secret:
    - DATABASE_URL

In this setup, we define the service name, the targeted Docker registry image, the VPS IP addresses under the web tier, and the proxy settings including automatic SSL issuance for the specified host domain.

Step 3: Server Provisioning and Dependency Setup

One of Kamal's greatest strengths is its ability to bootstrap raw servers. You do not need to manually install Docker on your new VPS. Execute the setup command:

kamal setup

This single command executes a comprehensive sequence: it establishes secure SSH connections, installs Docker if it is missing from the host machine, configures the Kamal Proxy daemon, initializes the Let's Encrypt SSL challenges, and handles initial environment variable provisioning.

How Kamal 2 Achieves Zero-Downtime Deployments

During subsequent updates, running kamal deploy triggers a highly coordinated workflow designed to prevent user-facing errors or dropped requests:

  1. Build and Push: Kamal builds the new Docker image locally or in your CI pipeline and pushes it to your remote container registry.
  2. Pull and Pre-boot: The targeted VPS pulls the new image and boots up the new container version on an isolated, internal port parallel to the running production container.
  3. Health Checking: The Kamal Proxy repeatedly queries the designated health check endpoint of the new container until it returns a successful 200 OK status.
  4. Hot-Swapping Traffic: Once confirmed healthy, the proxy immediately redirects new incoming HTTP/HTTPS traffic to the new container.
  5. Graceful Shutdown: The old container is allowed a configurable grace period to finish processing active, long-lived connections before being safely stopped and purged.

Comparing the Paradigms: Kamal vs. Kubernetes

To contextualize where Kamal 2 fits within modern infrastructure planning, consider the fundamental trade-offs:

  • Complexity and Maintenance: Kubernetes requires continuous maintenance, security patching of the control plane, and complex networking configurations. Kamal 2 requires zero maintenance overhead; it is stateless and runs only when you execute a command.
  • Resource Efficiency: Kubernetes components consume significant RAM and CPU idling costs on every node. Kamal 2 uses standard Docker containers overseen by an incredibly lightweight Go-based proxy, leaving maximum server resources available for your application workloads.
  • Scaling Flexibility: K8s excels at horizontal auto-scaling based on metric thresholds. Kamal 2 handles scaling statically: to scale out, you simply append a new VPS IP address to your deploy.yml file and run kamal server bootstrap.

Conclusion: Is Kamal 2 Right For Your Team?

Kamal 2 represents a major milestone for pragmatic engineering. By eliminating the structural bloat of container orchestration platforms while preserving the benefits of isolated Docker environments, it empowers modern development teams to manage high-traffic production workloads autonomously on affordable Cloud VPS infrastructure.

If your application requires dynamic multi-region routing or automated microservice auto-scaling, Kubernetes remains an industry gold standard. However, for the vast majority of SaaS platforms, API backends, and monolith structures, Kamal 2 delivers a fast, stable, and incredibly cost-effective deployment workflow that simplifies infrastructure and returns focus back to shipping code.

Deploying Kamal 2 on Cloud VPS: How Basecamp Deploys Production Apps Without Kubernetes | DPTCloud