Zum Hauptinhalt springen
Echtzeit-Radar & Feeds
Alle RSS Feeds ➔
👥 Community & Social
Windows Tipps & SecurityGrafikkarte vor Überhitzung schützen: So geht’s(25.09.2026 um 08:00 Uhr)
••••••••••
Windows Tipps & SecurityGrafikkarte vor Überhitzung schützen: So geht’s(25.09.2026 um 08:00 Uhr)
••••••••••
Intelligence View
⚡ tsecurity.de Intelligence

Deploying a Rails API-Only App with Postgres using Kamal 2

In this article, we'll walk through the steps to deploy a Rails API-only application using Kamal. Whether you're a seasoned developer or someone who's just discovered that "bundle install" isn't a jewelry store promotion, this guide will…

0
↗ Quelle (dev.to)
Reagiere als Erste:r — dein Feedback zählt!

In this article, we'll walk through the steps to deploy a Rails API-only application using Kamal. Whether you're a seasoned developer or someone who's just discovered that "bundle install" isn't a jewelry store promotion, this guide will help you get your app up and running in no time.






Prerequisites



A locally working Ruby on Rails app (rails 7 in this example).

This app, for this example, we won't use redis so if you use action cable, you need to have solid_cable configured. And for jobs, solid_queue (I use both here)

Docker Installed: Kamal uses Docker, so you'll need Docker installed. No, you can't skip this step—Docker is the star of this show!

A Server with SSH Access (DigitalOcean here). Think of it as your app's new home.

A container registry in DigitalOcean.





Configuring Kamal



Add this to your gemfile:




gem 'kamal', require: false
gem 'thruster', require: false






Then




bundle install
kamal init






This will create a couple of files:




  • config/deploy.yml

  • .kamal/secrets



config/deploy.yml should look like this (make sure to update the IPs and the env vars accordingly):




service: your_app_name_api

image: your_user/your_app_name_api

servers:
web:
- 199.xxx.xxx.xx
proxy:
ssl: false
registry:
server: registry.digitalocean.com
username: your_user
password:
- KAMAL_REGISTRY_PASSWORD

builder:
arch: amd64

# Inject ENV variables into containers (secrets come from .kamal/secrets).
env:
secret:
- RAILS_MASTER_KEY
- POSTGRES_PASSWORD
clear:
SOLID_QUEUE_IN_PUMA: true
DB_HOST: your_app_name_api-db

aliases:
console: app exec --interactive --reuse "bin/rails console"
shell: app exec --interactive --reuse "bash"
logs: app logs -f
dbc: app exec --interactive --reuse "bin/rails dbconsole"

volumes:
- "your_app_name_api_storage:/app/storage"

accessories:
db:
image: postgres:17
host: 199.xxx.xxx.xx
port: 127.0.0.1:5432:5432
env:
clear:
POSTGRES_USER: your_app_name_api
POSTGRES_DB: your_app_name_api_production
POSTGRES_HOST_AUTH_METHOD: trust
secret:
- YOUR_APP_NAME_API_DATABASE_PASSWORD
files:
- config/init.sql:/docker-entrypoint-initdb.d/setup.sql
directories:
- data:/var/lib/postgresql/data







And in .kamal/secrets add:




KAMAL_REGISTRY_PASSWORD=dop_v1_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
RAILS_MASTER_KEY=$(cat config/master.key)
YOUR_APP_NAME_API_DATABASE_PASSWORD=anythingyouwant
POSTGRES_PASSWORD=anythingyouwant






You will need a couple of additional files. Run this in your terminal:




touch bin/thrust
touch bin/docker-entrypoint
touch Dockerfile
touch config/init.sql






In bin/thrust add:




#!/usr/bin/env ruby
require "rubygems"
require "bundler/setup"

load Gem.bin_path("thruster", "thrust")






In bin/docker-entrypoint add:




#!/bin/bash -e

# Enable jemalloc for reduced memory usage and latency.
if [ -z "${LD_PRELOAD+x}" ]; then
LD_PRELOAD=$(find /usr/lib -name libjemalloc.so.2 -print -quit)
export LD_PRELOAD
fi

# If running the rails server then create or migrate existing db
if [ "${@: -2:1}" == "./bin/rails" ] && [ "${@: -1:1}" == "server" ]; then
./bin/rails db:prepare
fi

exec "${@}"






The Dockerfile, since it's an api only app, this will be enough:




# syntax=docker/dockerfile:1
# check=error=true

# This Dockerfile is designed for production, not development. Use with Kamal or build'n'run by hand:
# docker build -t your_app_name_api .
# docker run -d -p 80:80 -e RAILS_MASTER_KEY=<value from config/master.key> --name your_app_name_api your_app_name_api

# For a containerized dev environment, see Dev Containers: https://guides.rubyonrails.org/getting_started_with_devcontainer.html

# Make sure RUBY_VERSION matches the Ruby version in .ruby-version
ARG RUBY_VERSION=3.3.1
FROM docker.io/library/ruby:$RUBY_VERSION-slim AS base

# Rails app lives here
WORKDIR /rails

# Install base packages
RUN apt-get update -qq && \
apt-get install --no-install-recommends -y curl libjemalloc2 libvips libpq-dev postgresql-client && \
rm -rf /var/lib/apt/lists /var/cache/apt/archives

# Set production environment
ENV RAILS_ENV="production" \
BUNDLE_DEPLOYMENT="1" \
BUNDLE_PATH="/usr/local/bundle" \
BUNDLE_WITHOUT="development"

# Throw-away build stage to reduce size of final image
FROM base AS build

# Install packages needed to build gems
RUN apt-get update -qq && \
apt-get install --no-install-recommends -y build-essential git libpq-dev pkg-config && \
rm -rf /var/lib/apt/lists /var/cache/apt/archives

# Install application gems
COPY Gemfile Gemfile.lock ./
RUN bundle install && \
rm -rf ~/.bundle/ "${BUNDLE_PATH}"/ruby/*/cache "${BUNDLE_PATH}"/ruby/*/bundler/gems/*/.git && \
bundle exec bootsnap precompile --gemfile

# Copy application code
COPY . .

# Precompile bootsnap code for faster boot times
RUN bundle exec bootsnap precompile app/ lib/


# Final stage for app image
FROM base

# Copy built artifacts: gems, application
COPY --from=build "${BUNDLE_PATH}" "${BUNDLE_PATH}"
COPY --from=build /rails /rails

# Run and own only the runtime files as a non-root user for security
RUN groupadd --system --gid 1000 rails && \
useradd rails --uid 1000 --gid 1000 --create-home --shell /bin/bash && \
chown -R rails:rails db log storage tmp
USER 1000:1000

# Entrypoint prepares the database.
ENTRYPOINT ["/rails/bin/docker-entrypoint"]

# Start server via Thruster by default, this can be overwritten at runtime
EXPOSE 80
CMD ["./bin/thrust", "./bin/rails", "server"]






Finally, in config/init.sql add:




CREATE DATABASE your_app_name_api_production;
CREATE DATABASE your_app_name_api_production_cable;






Next step is to make sure your database.yml matches the deploy configuration:




production:
primary: &primary_production
<<: *default
database: your_app_name_api_production
username: your_app_name_api
password: your_app_name_api_password
host: your_app_name_api-db
cable:
<<: *primary_production
database: your_app_name_api_production_cable
migrations_paths: db/cable_migrate






You will also need to make sure that config/environments/production.rb has:




  config.assume_ssl = true
config.force_ssl = true
config.solid_queue.connects_to = { database: { writing: :production } } # in case you are using solid_queue






If you don't have a commited file in storage/ you will need to add one:




touch storage/.keep









Deploy



Afte commiting all changes with git, we are ready to go:




kamal setup






After a few minutes, you should see your app deployed =)

1. Sofort-Triage & Abwehrmaßnahmen

SOC Incident Playbook: Remote Code Execution (RCE) Defense
Syntax validiert (0 Fehler)
title: Detect Exploitation - Deploying a Rails API-Only App with Postgres using Kamal 2
id: 239dbd37-12e7-4930-8092-a5b81865c30d
status: experimental
description: Automatisch generierte SIEM-Erkennungsregel basierend auf CTI Intelligence
references:
  - https://tsecurity.de/
author: iShareStuff CTI Automated Detection Engine
date: 2026-09-26
logsource:
  category: network_connection
  product: any
detection:
  selection:
      CommandLine|contains:
        - 'exploit'
  condition: selection
falsepositives:
  - Legitime administrative Zugriffe oder Penetrationstests
level: high
tags:
  - attack.initial_access
Syntax validiert (0 Fehler)
rule CTI_Threat_Indicator {
    meta:
        author = "iShareStuff CTI Automated Detection Engine"
        date = "2026-09-26"
        description = "YARA Signature for "
    strings:
        $str = "Deploying a Rails API-Only App" ascii wide
    condition:
        any of them
}
Syntax validiert (0 Fehler)
index=security sourcetype IN ("cisco:asa", "pan:traffic", "zeek_conn", "suricata", "WinEventLog:Security")
("Deploying a Rails API-Only App with Post")
| stats count earliest(_time) as first_seen latest(_time) as last_seen by src_ip, dest_ip, dest_host, signature
| eval first_seen=strftime(first_seen, "%Y-%m-%d %H:%M:%S"), last_seen=strftime(last_seen, "%Y-%m-%d %H:%M:%S")
| sort - count
Syntax validiert (0 Fehler)
message: "*Deploying a Rails API-Only App with Post*"
Syntax validiert (0 Fehler)
CommonSecurityLog
| where Message has "Deploying a Rails API-Only App with Post"
| summarize EventCount = count(), FirstSeen = min(TimeGenerated), LastSeen = max(TimeGenerated) by SourceIP, DestinationIP, DestinationPort, Activity
| extend DetectionRule = "iShareStuff-CTI-Compiled"
| sort by EventCount desc

2. Cyber Threat Intelligence & Forensik

🎯
MITRE ATT&CK Matrix Navigator 14 Taktiken
Reconnaissance
-
Resource Development
-
Initial Access
Execution
Persistence
-
Privilege Escalation
Defense Evasion
Credential Access
-
Discovery
-
Lateral Movement
-
Collection
-
Command and Control
Exfiltration
-
Impact
tsecurity.de Cognitive Threat RAG
Fokus-Vektor:

Kognitive Analyse für identifizierte Bedrohung: Erhöhte Bedrohungslage im Bereich Deploying a Rails API-Only App with Post.... Basierend auf 368k Vektor-Korrelationen werden sofortige Isolationsmaßnahmen für betroffene Endpunkte empfohlen.

🛡️ Angriffsfläche & Exposure

Netzwerk/Remote-Zugriff ohne Vorauthentifizierung möglich.

⚡ Empfohlene Sofortmaßnahmen
  • 1. Perimeter-Inspektion: Relevante Portfreigaben und exponierte Endpunkte unverzüglich scannen.
  • 2. Patch-Applikation: Hersteller-Hotfix einspielen oder betroffene Daemons in isolierte DMZ-Segmente überführen.
  • 3. Telemetrie & EDR-Alerts: Prozessaufrufe und Child-Processes auf anomale Shell-Spawns überwachen.
🔗 Semantisch verwandte Zero-Days MariaDB 11.7 VEC
Ähnliche Beiträge
🔍 Verwandte News

Auch interessante Nachrichten Deploying a Rails API-Only App with Postgres using Kamal 2

Thematisch verwandte Begriffe: Deploying, Rails, APIOnly, with · 6 Treffer

Laden...

Videos werden geladen ...

Laden...

Beiträge werden geladen ...

Laden...

Videos werden geladen ...

Laden...

Beiträge werden geladen ...

Laden...

Videos werden geladen ...

Laden...

Beiträge werden geladen ...

Laden...

Videos werden geladen ...

Laden...

Beiträge werden geladen ...

Laden...

Videos werden geladen ...

Zum Aktualisieren ziehen
ZERO-DAY CVE-2026-88003 | InvoicePlane is a self-hosted open source application for managing invoi…
Advisory →
tsecurity.de Icon
Offline-Lesen, Eilmeldungen & 0ms Ladezeit

Installiere tsecurity.de direkt auf deinen Home-Bildschirm für das ultimative Vollbild-Magazinerlebnis ohne Browser-Leisten.

Nächster Beitrag