Local dev infrastructure in isolated Podman pods β one script, zero Docker Desktop, zero compose files.
curl -fsSL https://raw.githubusercontent.com/mrmeaow/devpods/main/devpods.sh | bash -s -- up pg| Pod | Services | Ports | Guide |
|---|---|---|---|
dev-pg-pod |
PostgreSQL 16 Β· pgweb | 5432 Β· UI β 8081 |
Guide |
dev-mongo-pod |
MongoDB 7 (Replica Set) Β· mongo-express | 27017 Β· UI β 8082 |
Guide |
dev-redis-pod |
Redis 7 Β· RedisInsight | 6379 Β· UI β 8083 |
Guide |
dev-mail-pod |
Mailpit | SMTP 1025 Β· UI β 8025 |
Guide |
dev-seq-pod |
Seq | Ingest + UI β 5341 |
Guide |
dev-rmq-pod |
RabbitMQ 3 (management) | AMQP 5672 Β· UI β 15672 |
Guide |
dev-nats-pod |
NATS 2 + JetStream | 4222 Β· Monitor β 8222 |
Guide |
dev-sms-pod |
devsms | 4000 Β· 5153 |
Guide |
dev-minio-pod |
MinIO | 9000 Β· 9001 |
Guide |
All persistent data lives in ~/.devpods/<pod-name>/ β fully isolated from your project.
| Requirement | Notes |
|---|---|
| Podman β₯ 4.0 | Rootless works great |
| macOS | Podman machine is auto-initialised if missing |
| Linux | Rootless systemd socket is auto-started if needed |
No Docker. No Docker Desktop. No sudo.
# explicit target required
curl -fsSL https://raw.githubusercontent.com/mrmeaow/devpods/main/devpods.sh | bash -s -- up pg# via curl
curl -fsSL https://raw.githubusercontent.com/mrmeaow/devpods/main/devpods.sh | bash -s -- up pg
# or after cloning
bash devpods.sh up mongobash devpods.sh <command> [pod ... | all]
| Command | Description |
|---|---|
up [pod ...|all] |
Start selected pod(s) β idempotent, safe to re-run |
down [pod ...|all] |
Stop and remove selected pod(s) |
reset [pod ...|all] |
Stop selected pod(s) and delete all data |
status |
Show state + endpoints for every pod |
help |
Print usage |
pg / postgres β dev-pg-pod
mongo / mongodb β dev-mongo-pod
redis β dev-redis-pod
mail / mailpit β dev-mail-pod
seq β dev-seq-pod
rmq / rabbitmq β dev-rmq-pod
nats β dev-nats-pod
sms / devsms β dev-sms-pod
minio β dev-minio-pod
all β every pod above
bash devpods.sh up all # boot everything
bash devpods.sh up pg mongo # start only Postgres + MongoDB
bash devpods.sh down redis # stop Redis pod only
bash devpods.sh reset mongo # wipe MongoDB data and stop
bash devpods.sh status # pretty status tableThe SELinux/rootless issue we observed is addressed for MongoDB specifically: its data mount uses :Z,U and the container runs as the mongodb user (--user 999:999).
This avoids rootless entrypoint ownership errors like:
chown: changing ownership of "/proc/1/fd/2": Permission denied
After up, the script prints a full cheatsheet. Quick reference:
PostgreSQL postgresql://devuser:devpass@localhost:5432/devdb
pgweb http://localhost:8081
MongoDB mongodb://localhost:27017/?replicaSet=rs0
mongo-express http://localhost:8082 (admin / admin)
Redis redis://:devredis@localhost:6379
RedisInsight http://localhost:8083
Mailpit SMTP localhost:1025
Mailpit UI http://localhost:8025
Seq http://localhost:5341
RabbitMQ amqp://devuser:devpass@localhost:5672
RMQ Mgmt http://localhost:15672 (devuser / devpass)
NATS nats://localhost:4222
NATS Monitor http://localhost:8222
devsms API http://localhost:4000
devsms UI http://localhost:5153
MinIO API http://localhost:9000
MinIO Console http://localhost:9001
On first run, ~/.devpods/.env is created with safe defaults:
# ~/.devpods/.env
PG_USER=devuser
PG_PASS=devpass
PG_DB=devdb
REDIS_PASS=devredis
RMQ_USER=devuser
RMQ_PASS=devpass
MONGO_RS=rs0
ME_USER=admin
ME_PASS=admin
MINIO_ROOT_USER=devminio
MINIO_ROOT_PASS=devminio123
MINIO_BUCKET=devsmsEdit that file to override anything. It is never committed β it lives only on your machine.
npm install winston @datalust/winston-seqimport winston from "winston";
import { SeqTransport } from "@datalust/winston-seq";
export const logger = winston.createLogger({
level: "debug",
format: winston.format.combine(
winston.format.errors({ stack: true }),
winston.format.json(),
),
transports: [
new winston.transports.Console(),
new SeqTransport({
serverUrl: process.env.SEQ_URL ?? "http://localhost:5341",
handleExceptions: true,
handleRejections: true,
}),
],
});# Open a psql shell
podman exec -it dev-pg-pod-postgres psql -U devuser -d devdb
# Open mongosh
podman exec -it dev-mongo-pod-mongodb mongosh
# Redis CLI
podman exec -it dev-redis-pod-redis redis-cli -a devredis
# Tail logs for any service
podman logs -f dev-seq-pod-seq
podman logs -f dev-rmq-pod-rabbitmq
# Check replica set status
podman exec -it dev-mongo-pod-mongodb mongosh --eval "rs.status()"
# Inspect all pods
podman pod ps
# MinIO health
curl -I http://localhost:9000/minio/health/live
# devsms logs
podman logs -f dev-sms-pod-devsmsThe project includes a robust E2E test suite built with Vitest and tsx to validate infrastructure readiness, specifically focusing on MongoDB Replica Set features and ACID transactions.
Ensure your pods are up, then run:
npm install
npm test- Replica Set Validation: Ensures Mongo is running in
rs0mode. - ACID Transactions: Tests multi-document commits and rollbacks.
- Concurrency: Validates write conflicts and isolation levels.
- Schema Resilience: Tests implicit collection creation inside transactions.
The refactored devpods.sh includes advanced logic to ensure a smooth developer experience:
- Pull Resilience: Detects Docker Hub rate limits and automatically falls back to
mirror.gcr.iofor authenticated/unauthenticated pulls. - macOS Machine Manager: Automatically initialises and starts Podman machines if they are missing or stopped.
- Linux Socket Activation: Kicks the
podman.socketservice if the daemon is unresponsive. - Intelligent RS Init: MongoDB replica sets are only initiated if
rs.status()indicates they aren't already active, makingupperfectly idempotent. - Preflight Checks: Validates images and system requirements before touching any containers, preventing partial "dirty" starts.
~/.devpods/
βββ .env β credentials (auto-created, never committed)
βββ cheatsheet.txt β auto-generated connection summary
βββ dev-pg-pod/
β βββ postgres/ β PostgreSQL data
βββ dev-mongo-pod/
β βββ mongodb/ β MongoDB data
βββ dev-redis-pod/
β βββ redis/ β Redis AOF
β βββ redisinsight/ β RedisInsight state
βββ dev-seq-pod/
β βββ seq/ β Seq events
βββ dev-rmq-pod/
β βββ rabbitmq/ β RabbitMQ mnesia
βββ dev-nats-pod/
βββ nats/ β JetStream store + server.conf
PRs welcome. The entire setup is a single self-contained bash script β keep it that way.
- Fork β branch β edit
devpods.sh - Validate syntax:
bash -n devpods.sh - Test using the E2E suite:
npm test - Open a PR with a description of what pod/behaviour changed
Made with β€οΈ by Mr.Meaow
MIT