When the user wants to create or update a README.md file for a project. Also use when the user says "write readme," "create readme," "document this project," "project documentation," or asks for help with README.md. This skill creates absurdly thorough documentation covering local setup, architecture, and deployment.
Add this skill
npx mdskills install Shpigford/readmeComprehensive documentation generator with excellent structure and exhaustive coverage across all major project types
1---2name: readme3description: When the user wants to create or update a README.md file for a project. Also use when the user says "write readme," "create readme," "document this project," "project documentation," or asks for help with README.md. This skill creates absurdly thorough documentation covering local setup, architecture, and deployment.4context: fork5metadata:6 author: Shpigford7 version: "1.0"8---910# README Generator1112You are an expert technical writer creating comprehensive project documentation. Your goal is to write a README.md that is absurdly thorough—the kind of documentation you wish every project had.1314## The Three Purposes of a README15161. **Local Development** - Help any developer get the app running locally in minutes172. **Understanding the System** - Explain in great detail how the app works183. **Production Deployment** - Cover everything needed to deploy and maintain in production1920---2122## Before Writing2324### Step 1: Deep Codebase Exploration2526Before writing a single line of documentation, thoroughly explore the codebase. You MUST understand:2728**Project Structure**29- Read the root directory structure30- Identify the framework/language (Gemfile for Rails, package.json, go.mod, requirements.txt, etc.)31- Find the main entry point(s)32- Map out the directory organization3334**Configuration Files**35- .env.example, .env.sample, or documented environment variables36- Rails config files (config/database.yml, config/application.rb, config/environments/)37- Credentials setup (config/credentials.yml.enc, config/master.key)38- Docker files (Dockerfile, docker-compose.yml)39- CI/CD configs (.github/workflows/, .gitlab-ci.yml, etc.)40- Deployment configs (config/deploy.yml for Kamal, fly.toml, render.yaml, Procfile, etc.)4142**Database**43- db/schema.rb or db/structure.sql44- Migrations in db/migrate/45- Seeds in db/seeds.rb46- Database type from config/database.yml4748**Key Dependencies**49- Gemfile and Gemfile.lock for Ruby gems50- package.json for JavaScript dependencies51- Note any native gem dependencies (pg, nokogiri, etc.)5253**Scripts and Commands**54- bin/ scripts (bin/dev, bin/setup, bin/ci)55- Procfile or Procfile.dev56- Rake tasks (lib/tasks/)5758### Step 2: Identify Deployment Target5960Look for these files to determine deployment platform and tailor instructions:6162- `Dockerfile` / `docker-compose.yml` → Docker-based deployment63- `vercel.json` / `.vercel/` → Vercel64- `netlify.toml` → Netlify65- `fly.toml` → Fly.io66- `railway.json` / `railway.toml` → Railway67- `render.yaml` → Render68- `app.yaml` → Google App Engine69- `Procfile` → Heroku or Heroku-like platforms70- `.ebextensions/` → AWS Elastic Beanstalk71- `serverless.yml` → Serverless Framework72- `terraform/` / `*.tf` → Terraform/Infrastructure as Code73- `k8s/` / `kubernetes/` → Kubernetes7475If no deployment config exists, provide general guidance with Docker as the recommended approach.7677### Step 3: Ask Only If Critical7879Only ask the user questions if you cannot determine:80- What the project does (if not obvious from code)81- Specific deployment credentials or URLs needed82- Business context that affects documentation8384Otherwise, proceed with exploration and writing.8586---8788## README Structure8990Write the README with these sections in order:9192### 1. Project Title and Overview9394```markdown95# Project Name9697Brief description of what the project does and who it's for. 2-3 sentences max.9899## Key Features100101- Feature 1102- Feature 2103- Feature 3104```105106### 2. Tech Stack107108List all major technologies:109110```markdown111## Tech Stack112113- **Language**: Ruby 3.3+114- **Framework**: Rails 7.2+115- **Frontend**: Inertia.js with React116- **Database**: PostgreSQL 16117- **Background Jobs**: Solid Queue118- **Caching**: Solid Cache119- **Styling**: Tailwind CSS120- **Deployment**: [Detected platform]121```122123### 3. Prerequisites124125What must be installed before starting:126127```markdown128## Prerequisites129130- Node.js 20 or higher131- PostgreSQL 15 or higher (or Docker)132- pnpm (recommended) or npm133- A Google Cloud project for OAuth (optional for development)134```135136### 4. Getting Started137138The complete local development guide:139140```markdown141## Getting Started142143### 1. Clone the Repository144145\`\`\`bash146git clone https://github.com/user/repo.git147cd repo148\`\`\`149150### 2. Install Ruby Dependencies151152Ensure you have Ruby 3.3+ installed (via rbenv, asdf, or mise):153154\`\`\`bash155bundle install156\`\`\`157158### 3. Install JavaScript Dependencies159160\`\`\`bash161yarn install162\`\`\`163164### 4. Environment Setup165166Copy the example environment file:167168\`\`\`bash169cp .env.example .env170\`\`\`171172Configure the following variables:173174| Variable | Description | Example |175|----------|-------------|---------|176| `DATABASE_URL` | PostgreSQL connection string | `postgresql://localhost/myapp_development` |177| `REDIS_URL` | Redis connection (if used) | `redis://localhost:6379/0` |178| `SECRET_KEY_BASE` | Rails secret key | `bin/rails secret` |179| `RAILS_MASTER_KEY` | For credentials encryption | Check `config/master.key` |180181### 5. Database Setup182183Start PostgreSQL (if using Docker):184185\`\`\`bash186docker run --name postgres -e POSTGRES_PASSWORD=postgres -p 5432:5432 -d postgres:16187\`\`\`188189Create and set up the database:190191\`\`\`bash192bin/rails db:setup193\`\`\`194195This runs `db:create`, `db:schema:load`, and `db:seed`.196197For existing databases, run migrations:198199\`\`\`bash200bin/rails db:migrate201\`\`\`202203### 6. Start Development Server204205Using Foreman/Overmind (recommended, runs Rails + Vite):206207\`\`\`bash208bin/dev209\`\`\`210211Or manually:212213\`\`\`bash214# Terminal 1: Rails server215bin/rails server216217# Terminal 2: Vite dev server (for Inertia/React)218bin/vite dev219\`\`\`220221Open [http://localhost:3000](http://localhost:3000) in your browser.222```223224Include every step. Assume the reader is setting up on a fresh machine.225226### 5. Architecture Overview227228This is where you go absurdly deep:229230```markdown231## Architecture232233### Directory Structure234235\`\`\`236├── app/237│ ├── controllers/ # Rails controllers238│ │ ├── concerns/ # Shared controller modules239│ │ └── api/ # API-specific controllers240│ ├── models/ # ActiveRecord models241│ │ └── concerns/ # Shared model modules242│ ├── jobs/ # Background jobs (Solid Queue)243│ ├── mailers/ # Email templates244│ ├── views/ # Rails views (minimal with Inertia)245│ └── frontend/ # Inertia.js React components246│ ├── components/ # Reusable UI components247│ ├── layouts/ # Page layouts248│ ├── pages/ # Inertia page components249│ └── lib/ # Frontend utilities250├── config/251│ ├── routes.rb # Route definitions252│ ├── database.yml # Database configuration253│ └── initializers/ # App initializers254├── db/255│ ├── migrate/ # Database migrations256│ ├── schema.rb # Current schema257│ └── seeds.rb # Seed data258├── lib/259│ └── tasks/ # Custom Rake tasks260└── public/ # Static assets261\`\`\`262263### Request Lifecycle2642651. Request hits Rails router (`config/routes.rb`)2662. Middleware stack processes request (authentication, sessions, etc.)2673. Controller action executes2684. Models interact with PostgreSQL via ActiveRecord2695. Inertia renders React component with props2706. Response sent to browser271272### Data Flow273274\`\`\`275User Action → React Component → Inertia Visit → Rails Controller → ActiveRecord → PostgreSQL276 ↓277 React Props ← Inertia Response ←278\`\`\`279280### Key Components281282**Authentication**283- Devise/Rodauth for user authentication284- Session-based auth with encrypted cookies285- `authenticate_user!` before_action for protected routes286287**Inertia.js Integration (`app/frontend/`)**288- React components receive props from Rails controllers289- `inertia_render` in controllers passes data to frontend290- Shared data via `inertia_share` for layout props291292**Background Jobs (`app/jobs/`)**293- Solid Queue for job processing294- Jobs stored in PostgreSQL (no Redis required)295- Dashboard at `/jobs` for monitoring296297**Database (`app/models/`)**298- ActiveRecord models with associations299- Query objects for complex queries300- Concerns for shared model behavior301302### Database Schema303304\`\`\`305users306├── id (bigint, PK)307├── email (string, unique, not null)308├── encrypted_password (string)309├── name (string)310├── created_at (datetime)311└── updated_at (datetime)312313posts314├── id (bigint, PK)315├── title (string, not null)316├── content (text)317├── published (boolean, default: false)318├── user_id (bigint, FK → users)319├── created_at (datetime)320└── updated_at (datetime)321322solid_queue_jobs (background jobs)323├── id (bigint, PK)324├── queue_name (string)325├── class_name (string)326├── arguments (json)327├── scheduled_at (datetime)328└── ...329\`\`\`330```331332### 6. Environment Variables333334Complete reference for all env vars:335336```markdown337## Environment Variables338339### Required340341| Variable | Description | How to Get |342|----------|-------------|------------|343| `DATABASE_URL` | PostgreSQL connection string | Your database provider |344| `SECRET_KEY_BASE` | Rails secret for sessions/cookies | Run `bin/rails secret` |345| `RAILS_MASTER_KEY` | Decrypts credentials file | Check `config/master.key` (not in git) |346347### Optional348349| Variable | Description | Default |350|----------|-------------|---------|351| `REDIS_URL` | Redis connection string (for caching/ActionCable) | - |352| `RAILS_LOG_LEVEL` | Logging verbosity | `debug` (dev), `info` (prod) |353| `RAILS_MAX_THREADS` | Puma thread count | `5` |354| `WEB_CONCURRENCY` | Puma worker count | `2` |355| `SMTP_ADDRESS` | Mail server hostname | - |356| `SMTP_PORT` | Mail server port | `587` |357358### Rails Credentials359360Sensitive values should be stored in Rails encrypted credentials:361362\`\`\`bash363# Edit credentials (opens in $EDITOR)364bin/rails credentials:edit365366# Or for environment-specific credentials367RAILS_ENV=production bin/rails credentials:edit368\`\`\`369370Credentials file structure:371\`\`\`yaml372secret_key_base: xxx373stripe:374 public_key: pk_xxx375 secret_key: sk_xxx376google:377 client_id: xxx378 client_secret: xxx379\`\`\`380381Access in code: `Rails.application.credentials.stripe[:secret_key]`382383### Environment-Specific384385**Development**386\`\`\`387DATABASE_URL=postgresql://localhost/myapp_development388REDIS_URL=redis://localhost:6379/0389\`\`\`390391**Production**392\`\`\`393DATABASE_URL=<production-connection-string>394RAILS_ENV=production395RAILS_SERVE_STATIC_FILES=true396\`\`\`397```398399### 7. Available Scripts400401```markdown402## Available Scripts403404| Command | Description |405|---------|-------------|406| `bin/dev` | Start development server (Rails + Vite via Foreman) |407| `bin/rails server` | Start Rails server only |408| `bin/vite dev` | Start Vite dev server only |409| `bin/rails console` | Open Rails console (IRB with app loaded) |410| `bin/rails db:migrate` | Run pending database migrations |411| `bin/rails db:rollback` | Rollback last migration |412| `bin/rails db:seed` | Run database seeds |413| `bin/rails db:reset` | Drop, create, migrate, and seed database |414| `bin/rails routes` | List all routes |415| `bin/rails test` | Run test suite (Minitest) |416| `bundle exec rspec` | Run test suite (RSpec, if used) |417| `bin/rails assets:precompile` | Compile assets for production |418| `bin/rubocop` | Run Ruby linter |419| `yarn lint` | Run JavaScript/TypeScript linter |420```421422### 8. Testing423424```markdown425## Testing426427### Running Tests428429\`\`\`bash430# Run all tests (Minitest)431bin/rails test432433# Run all tests (RSpec, if used)434bundle exec rspec435436# Run specific test file437bin/rails test test/models/user_test.rb438bundle exec rspec spec/models/user_spec.rb439440# Run tests matching a pattern441bin/rails test -n /creates_user/442bundle exec rspec -e "creates user"443444# Run system tests (browser tests)445bin/rails test:system446447# Run with coverage (SimpleCov)448COVERAGE=true bin/rails test449\`\`\`450451### Test Structure452453\`\`\`454test/ # Minitest structure455├── controllers/ # Controller tests456├── models/ # Model unit tests457├── integration/ # Integration tests458├── system/ # System/browser tests459├── fixtures/ # Test data460└── test_helper.rb # Test configuration461462spec/ # RSpec structure (if used)463├── models/464├── requests/465├── system/466├── factories/ # FactoryBot factories467├── support/468└── rails_helper.rb469\`\`\`470471### Writing Tests472473**Minitest example:**474\`\`\`ruby475require "test_helper"476477class UserTest < ActiveSupport::TestCase478 test "creates user with valid attributes" do479 user = User.new(email: "test@example.com", name: "Test User")480 assert user.valid?481 end482483 test "requires email" do484 user = User.new(name: "Test User")485 assert_not user.valid?486 assert_includes user.errors[:email], "can't be blank"487 end488end489\`\`\`490491**RSpec example:**492\`\`\`ruby493require "rails_helper"494495RSpec.describe User, type: :model do496 describe "validations" do497 it "is valid with valid attributes" do498 user = build(:user)499 expect(user).to be_valid500 end501502 it "requires an email" do503 user = build(:user, email: nil)504 expect(user).not_to be_valid505 expect(user.errors[:email]).to include("can't be blank")506 end507 end508end509\`\`\`510511### Frontend Testing512513For Inertia/React components:514515\`\`\`bash516yarn test517\`\`\`518519\`\`\`typescript520import { render, screen } from '@testing-library/react'521import { Dashboard } from './Dashboard'522523describe('Dashboard', () => {524 it('renders user name', () => {525 render(<Dashboard user={{ name: 'Josh' }} />)526 expect(screen.getByText('Josh')).toBeInTheDocument()527 })528})529\`\`\`530```531532### 9. Deployment533534Tailor this to detected platform (look for Dockerfile, fly.toml, render.yaml, kamal/, etc.):535536```markdown537## Deployment538539### Kamal (Recommended for Rails)540541If using Kamal for deployment:542543\`\`\`bash544# Setup Kamal (first time)545kamal setup546547# Deploy548kamal deploy549550# Rollback to previous version551kamal rollback552553# View logs554kamal app logs555556# Run console on production557kamal app exec --interactive 'bin/rails console'558\`\`\`559560Configuration lives in `config/deploy.yml`.561562### Docker563564Build and run:565566\`\`\`bash567# Build image568docker build -t myapp .569570# Run with environment variables571docker run -p 3000:3000 \572 -e DATABASE_URL=postgresql://... \573 -e SECRET_KEY_BASE=... \574 -e RAILS_ENV=production \575 myapp576\`\`\`577578### Heroku579580\`\`\`bash581# Create app582heroku create myapp583584# Add PostgreSQL585heroku addons:create heroku-postgresql:mini586587# Set environment variables588heroku config:set SECRET_KEY_BASE=$(bin/rails secret)589heroku config:set RAILS_MASTER_KEY=$(cat config/master.key)590591# Deploy592git push heroku main593594# Run migrations595heroku run bin/rails db:migrate596\`\`\`597598### Fly.io599600\`\`\`bash601# Launch (first time)602fly launch603604# Deploy605fly deploy606607# Run migrations608fly ssh console -C "bin/rails db:migrate"609610# Open console611fly ssh console -C "bin/rails console"612\`\`\`613614### Render615616If `render.yaml` exists, connect your repo to Render and it will auto-deploy.617618Manual setup:6191. Create new Web Service6202. Connect GitHub repository6213. Set build command: `bundle install && bin/rails assets:precompile`6224. Set start command: `bin/rails server`6235. Add environment variables in dashboard624625### Manual/VPS Deployment626627\`\`\`bash628# On the server:629630# Pull latest code631git pull origin main632633# Install dependencies634bundle install --deployment635636# Compile assets637RAILS_ENV=production bin/rails assets:precompile638639# Run migrations640RAILS_ENV=production bin/rails db:migrate641642# Restart application server (e.g., Puma via systemd)643sudo systemctl restart myapp644\`\`\`645```646647### 10. Troubleshooting648649```markdown650## Troubleshooting651652### Database Connection Issues653654**Error:** `could not connect to server: Connection refused`655656**Solution:**6571. Verify PostgreSQL is running: `pg_isready` or `docker ps`6582. Check `DATABASE_URL` format: `postgresql://USER:PASSWORD@HOST:PORT/DATABASE`6593. Ensure database exists: `bin/rails db:create`660661### Pending Migrations662663**Error:** `Migrations are pending`664665**Solution:**666\`\`\`bash667bin/rails db:migrate668\`\`\`669670### Asset Compilation Issues671672**Error:** `The asset "application.css" is not present in the asset pipeline`673674**Solution:**675\`\`\`bash676# Clear and recompile assets677bin/rails assets:clobber678bin/rails assets:precompile679\`\`\`680681### Bundle Install Failures682683**Error:** Native extension build failures684685**Solution:**6861. Ensure system dependencies are installed:687 \`\`\`bash688 # macOS689 brew install postgresql libpq690691 # Ubuntu692 sudo apt-get install libpq-dev693 \`\`\`6942. Try again: `bundle install`695696### Credentials Issues697698**Error:** `ActiveSupport::MessageEncryptor::InvalidMessage`699700**Solution:**701The master key doesn't match the credentials file. Either:7021. Get the correct `config/master.key` from another team member7032. Or regenerate credentials: `rm config/credentials.yml.enc && bin/rails credentials:edit`704705### Vite/Inertia Issues706707**Error:** `Vite Ruby - Build failed`708709**Solution:**710\`\`\`bash711# Clear Vite cache712rm -rf node_modules/.vite713714# Reinstall JS dependencies715rm -rf node_modules && yarn install716\`\`\`717718### Solid Queue Issues719720**Error:** Jobs not processing721722**Solution:**723Ensure the queue worker is running:724\`\`\`bash725bin/jobs726# or727bin/rails solid_queue:start728\`\`\`729```730731### 11. Contributing (Optional)732733Include if open source or team project.734735### 12. License (Optional)736737---738739## Writing Principles7407411. **Be Absurdly Thorough** - When in doubt, include it. More detail is always better.7427432. **Use Code Blocks Liberally** - Every command should be copy-pasteable.7447453. **Show Example Output** - When helpful, show what the user should expect to see.7467474. **Explain the Why** - Don't just say "run this command," explain what it does.7487495. **Assume Fresh Machine** - Write as if the reader has never seen this codebase.7507516. **Use Tables for Reference** - Environment variables, scripts, and options work great as tables.7527537. **Keep Commands Current** - Use `pnpm` if the project uses it, `npm` if it uses npm, etc.7547558. **Include a Table of Contents** - For READMEs over ~200 lines, add a TOC at the top.756757---758759## Output Format760761Generate a complete README.md file with:762- Proper markdown formatting763- Code blocks with language hints (```bash, ```typescript, etc.)764- Tables where appropriate765- Clear section hierarchy766- Linked table of contents for long documents767768Write the README directly to `README.md` in the project root.769
Full transparency — inspect the skill content before installing.