start-vibing-stacks 2.32.0 → 2.34.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,260 @@
1
+ ---
2
+ name: podman-patterns
3
+ version: 1.0.0
4
+ description: "Podman 2026 patterns: rootless containers (no daemon, no root), Quadlet (systemd units), podman play kube, podman compose (Docker Compose compatibility), podman machine (macOS/Windows), healthchecks, secrets via --secret, distroless images. Replaces Docker daemon in CI and production for security and simplicity."
5
+ ---
6
+
7
+ # Podman Patterns (2026)
8
+
9
+ **Invoke when writing container definitions, systemd services for containers, Kubernetes manifests for single pods, or migrating from Docker daemon.**
10
+
11
+ > 2026 reality: **Rootless is the default**. No container runtime should run as root. Podman + Quadlet is the recommended path on Linux for production services. `podman play kube` replaces simple `kubectl apply` for single-pod workloads. Dockerfiles are fully compatible.
12
+
13
+ ## Why Podman in 2026
14
+
15
+ | Aspect | Docker | Podman | Winner |
16
+ |--------|--------|--------|--------|
17
+ | Daemon | Required (root) | None | Podman |
18
+ | Root | Required for daemon | Rootless by default | Podman |
19
+ | Kubernetes | Separate (kind/minikube) | `podman play kube` | Podman |
20
+ | Systemd | Manual units | Quadlet (native) | Podman |
21
+ | macOS/Windows | Docker Desktop | `podman machine` | Tie |
22
+ | CI | Docker-in-Docker | Native rootless | Podman |
23
+
24
+ **Rule:** If the target is Linux (server or CI), prefer Podman. If you need Docker Compose syntax, use `podman compose` — it is a drop-in replacement.
25
+
26
+ ---
27
+
28
+ ## 1. Rootless + Distroless (Node.js example)
29
+
30
+ ```dockerfile
31
+ # syntax=docker/dockerfile:1.7
32
+ ARG NODE_VERSION=22.11.0
33
+
34
+ FROM node:${NODE_VERSION}-alpine AS builder
35
+ WORKDIR /app
36
+ COPY package*.json ./
37
+ RUN --mount=type=cache,target=/root/.npm \
38
+ npm ci --ignore-scripts
39
+ COPY . .
40
+ RUN npm run build && npm prune --omit=dev
41
+
42
+ FROM gcr.io/distroless/nodejs22-debian12:nonroot
43
+ WORKDIR /app
44
+ COPY --from=builder --chown=nonroot:nonroot /app/node_modules ./node_modules
45
+ COPY --from=builder --chown=nonroot:nonroot /app/dist ./dist
46
+ COPY --from=builder --chown=nonroot:nonroot /app/package.json ./
47
+ USER nonroot
48
+ EXPOSE 3000
49
+ ENV NODE_ENV=production
50
+ HEALTHCHECK --interval=30s --timeout=3s --start-period=5s --retries=3 \
51
+ CMD ["/nodejs/bin/node", "-e", "fetch('http://127.0.0.1:3000/healthz').then(r=>process.exit(r.ok?0:1)).catch(()=>process.exit(1))"]
52
+ CMD ["dist/server.js"]
53
+ ```
54
+
55
+ Run rootless:
56
+
57
+ ```bash
58
+ podman run -d --name app \
59
+ --user 10001:10001 \
60
+ --read-only \
61
+ --security-opt no-new-privileges \
62
+ -p 3000:3000 \
63
+ localhost/myapp:latest
64
+ ```
65
+
66
+ ---
67
+
68
+ ## 2. Quadlet — The 2026 Way to Run Containers as Services
69
+
70
+ Instead of writing systemd units by hand, use **Quadlet** (`.container` files).
71
+
72
+ ### Example: `myapp.container`
73
+
74
+ ```ini
75
+ [Unit]
76
+ Description=My Node.js App
77
+ After=network-online.target
78
+ Wants=network-online.target
79
+
80
+ [Container]
81
+ Image=localhost/myapp:latest
82
+ ContainerName=myapp
83
+ PublishPort=3000:3000
84
+ Environment=NODE_ENV=production
85
+ HealthCmd=/nodejs/bin/node -e "fetch('http://127.0.0.1:3000/healthz').then(r=>process.exit(r.ok?0:1)).catch(()=>process.exit(1))"
86
+ HealthInterval=30s
87
+ HealthTimeout=3s
88
+ HealthStartPeriod=5s
89
+ HealthRetries=3
90
+ ReadOnly=true
91
+ User=10001
92
+ Group=10001
93
+ SecurityLabelDisable=false
94
+
95
+ [Service]
96
+ Restart=always
97
+ RestartSec=5
98
+
99
+ [Install]
100
+ WantedBy=multi-user.target
101
+ ```
102
+
103
+ Install:
104
+
105
+ ```bash
106
+ sudo cp myapp.container /etc/containers/systemd/
107
+ sudo systemctl daemon-reload
108
+ sudo systemctl start myapp.service
109
+ ```
110
+
111
+ Quadlet automatically creates the proper systemd service, handles restarts, and integrates with `podman`.
112
+
113
+ ---
114
+
115
+ ## 3. `podman play kube` — Single-Pod Kubernetes
116
+
117
+ For simple workloads, avoid full Kubernetes. Use a Pod manifest:
118
+
119
+ ```yaml
120
+ apiVersion: v1
121
+ kind: Pod
122
+ metadata:
123
+ name: myapp
124
+ labels:
125
+ app: myapp
126
+ spec:
127
+ containers:
128
+ - name: app
129
+ image: localhost/myapp:latest
130
+ ports:
131
+ - containerPort: 3000
132
+ env:
133
+ - name: NODE_ENV
134
+ value: production
135
+ securityContext:
136
+ runAsNonRoot: true
137
+ runAsUser: 10001
138
+ readOnlyRootFilesystem: true
139
+ livenessProbe:
140
+ exec:
141
+ command:
142
+ - /nodejs/bin/node
143
+ - -e
144
+ - "fetch('http://127.0.0.1:3000/healthz').then(r=>process.exit(r.ok?0:1)).catch(()=>process.exit(1))"
145
+ initialDelaySeconds: 5
146
+ periodSeconds: 30
147
+ restartPolicy: Always
148
+ ```
149
+
150
+ Deploy:
151
+
152
+ ```bash
153
+ podman play kube myapp.yaml
154
+ ```
155
+
156
+ Stop:
157
+
158
+ ```bash
159
+ podman play kube --down myapp.yaml
160
+ ```
161
+
162
+ This is dramatically simpler than Helm or full K8s for single-service apps.
163
+
164
+ ---
165
+
166
+ ## 4. Secrets (Better Than Docker Build Secrets)
167
+
168
+ Podman supports `--secret` natively:
169
+
170
+ ```bash
171
+ podman run --secret id=stripe_key,src=.env.d/local/secrets/stripe.key \
172
+ -e STRIPE_SECRET_KEY_FILE=/run/secrets/stripe_key \
173
+ localhost/myapp
174
+ ```
175
+
176
+ Inside the container, the secret is available at `/run/secrets/stripe_key` and is never stored in the image layer.
177
+
178
+ See `secrets-management` for the full `.env.d/` + secret file pattern.
179
+
180
+ ---
181
+
182
+ ## 5. Podman Machine (macOS / Windows)
183
+
184
+ On non-Linux hosts:
185
+
186
+ ```bash
187
+ podman machine init
188
+ podman machine start
189
+ podman machine ssh # for debugging
190
+ ```
191
+
192
+ Use the same Dockerfiles and Quadlet files — Podman abstracts the VM.
193
+
194
+ ---
195
+
196
+ ## 6. Migration from Docker
197
+
198
+ | Docker Command | Podman Equivalent | Notes |
199
+ |----------------|-------------------|-------|
200
+ | `docker build` | `podman build` | Same syntax |
201
+ | `docker compose up` | `podman compose up` | Full compatibility |
202
+ | `docker run --user` | `podman run --user` | Rootless is default |
203
+ | Manual systemd unit | Quadlet `.container` | Much simpler |
204
+ | `docker ps` | `podman ps` | Identical output |
205
+ | `docker system prune` | `podman system prune` | Same |
206
+
207
+ **Rule:** Keep using `docker-compose.yml` if you want — just run it with `podman compose`. The compose file is unchanged.
208
+
209
+ ---
210
+
211
+ ## 7. Integration With Other Skills
212
+
213
+ - `secrets-management` — Use `.env.d/` + `--secret` mounts.
214
+ - `security-baseline` — Rootless + read-only + no-new-privileges is the baseline.
215
+ - `ci-pipelines` — Run `podman` instead of `docker` in GitHub Actions (no DinD needed).
216
+ - `docker-patterns` — Podman can consume the exact same Dockerfiles. The two skills are complementary.
217
+
218
+ ---
219
+
220
+ ## FORBIDDEN
221
+
222
+ | Pattern | Reason |
223
+ |---------|--------|
224
+ | Running Podman as root | Defeats the entire security model |
225
+ | Using `sudo podman` in scripts | Indicates misconfiguration |
226
+ | Storing secrets in image layers | Use `--secret` or mounted files |
227
+ | Running containers with `--privileged` | Never needed with rootless + proper capabilities |
228
+ | Ignoring healthchecks | Quadlet and `podman play kube` both support them natively |
229
+
230
+ ---
231
+
232
+ ## Pre-Deployment Checklist
233
+
234
+ - [ ] Image built with multi-stage + distroless/chiseled
235
+ - [ ] Non-root user (10001:10001 or higher)
236
+ - [ ] Read-only root filesystem
237
+ - [ ] Healthcheck defined
238
+ - [ ] Secrets passed via `--secret` (not ENV or COPY)
239
+ - [ ] If Linux server → Quadlet `.container` file
240
+ - [ ] If simple K8s workload → `podman play kube` manifest
241
+ - [ ] `.dockerignore` present (same as Docker)
242
+
243
+ ---
244
+
245
+ ## See Also
246
+
247
+ - `docker-patterns` — the Docker side of the same story (compatible)
248
+ - `secrets-management` — how to structure `.env.d/` and secret files
249
+ - `security-baseline` — rootless is now table stakes
250
+ - `ci-pipelines` — rootless CI runners
251
+
252
+ ---
253
+
254
+ ## Memory Optimization Trigger
255
+
256
+ If this skill grows beyond ~250 lines or accumulates many near-duplicate Quadlet examples, run:
257
+
258
+ ```bash
259
+ npx start-vibing-stacks memory optimize --dry-run
260
+ ```
@@ -0,0 +1,194 @@
1
+ ---
2
+ name: react-server-components
3
+ version: 1.0.0
4
+ description: "React 19 Server Components (RSC) production patterns for 2026: Server Components as default, 'use client' only on interactive leaves, streaming with Suspense, parallel data fetching with Promise.all, serialization rules (no functions/classes across boundary), layered caching (React cache + framework unstable_cache), Server Actions for mutations. Use with Next.js 16+ App Router."
5
+ ---
6
+
7
+ # React Server Components (2026 Production)
8
+
9
+ **Invoke when building any React 19+ application using the App Router (Next.js 16+, Remix RSC, TanStack Start, etc.).**
10
+
11
+ > 2026 reality: Server Components are the default. 40%+ bundle size reduction is common when done correctly. The mental model is: **Server Components fetch and render on the server. Client Components add interactivity. Keep the boundary small and explicit.**
12
+
13
+ ---
14
+
15
+ ## 1. The Core Mental Model
16
+
17
+ | Component Type | Runs Where | Bundle Impact | Data Fetching | Interactivity |
18
+ |----------------|------------|---------------|---------------|---------------|
19
+ | **Server Component** (default) | Server | 0 KB to client | Direct (DB, API, FS) | None |
20
+ | **Client Component** (`'use client'`) | Client | Full JS shipped | Via props or API | Full (useState, useEffect, etc.) |
21
+
22
+ **Rule of thumb:**
23
+ - Default to Server Component.
24
+ - Add `'use client'` **only** when you need interactivity, browser APIs, or hooks.
25
+ - Keep Client Components as **small leaf components** near the user interaction.
26
+
27
+ ---
28
+
29
+ ## 2. Data Fetching — No Waterfalls
30
+
31
+ **Wrong (sequential):**
32
+
33
+ ```tsx
34
+ // app/page.tsx
35
+ export default async function Page() {
36
+ const user = await getUser(); // 200ms
37
+ const posts = await getPosts(user); // waits for user
38
+ const comments = await getComments(); // waits for posts
39
+ return <Dashboard ... />;
40
+ }
41
+ ```
42
+
43
+ **Correct (parallel):**
44
+
45
+ ```tsx
46
+ export default async function Page() {
47
+ const [user, posts, comments] = await Promise.all([
48
+ getUser(),
49
+ getPosts(),
50
+ getComments(),
51
+ ]);
52
+ return <Dashboard user={user} posts={posts} comments={comments} />;
53
+ }
54
+ ```
55
+
56
+ Or use React's `cache()` for deduplication across the component tree.
57
+
58
+ ---
59
+
60
+ ## 3. Passing Data Across the Server → Client Boundary
61
+
62
+ **Only plain serializable data is allowed:**
63
+
64
+ - Primitives (`string`, `number`, `boolean`, `null`)
65
+ - Plain objects and arrays
66
+ - Dates (serialized as ISO strings in Next.js)
67
+ - Promises (React will suspend)
68
+
69
+ **Forbidden:**
70
+
71
+ - Functions
72
+ - Class instances
73
+ - `Map`, `Set`, `Date` (raw), `Error`, `RegExp`
74
+ - React elements (JSX) from Server to Client
75
+
76
+ **Correct pattern:**
77
+
78
+ ```tsx
79
+ // Server Component
80
+ const user = await getUser();
81
+ const safeUser = {
82
+ id: user.id,
83
+ name: user.name,
84
+ createdAt: user.createdAt.toISOString(),
85
+ };
86
+
87
+ return <UserProfile user={safeUser} />; // Client Component
88
+ ```
89
+
90
+ ---
91
+
92
+ ## 4. Streaming with Suspense
93
+
94
+ Slow data should be wrapped in `<Suspense>` so the rest of the page streams immediately.
95
+
96
+ ```tsx
97
+ import { Suspense } from 'react';
98
+ import { Comments } from './comments';
99
+
100
+ export default function Page() {
101
+ return (
102
+ <div>
103
+ <Header /> {/* streams first */}
104
+ <Suspense fallback={<CommentsSkeleton />}>
105
+ <Comments /> {/* streams when ready */}
106
+ </Suspense>
107
+ </div>
108
+ );
109
+ }
110
+ ```
111
+
112
+ ---
113
+
114
+ ## 5. Server Actions (`'use server'`)
115
+
116
+ For mutations, use Server Actions instead of API routes.
117
+
118
+ ```tsx
119
+ // app/actions.ts
120
+ 'use server';
121
+
122
+ export async function createPost(formData: FormData) {
123
+ const title = formData.get('title');
124
+ await db.post.create({ data: { title } });
125
+ revalidatePath('/posts');
126
+ }
127
+ ```
128
+
129
+ ```tsx
130
+ // app/new-post.tsx (Client Component)
131
+ 'use client';
132
+
133
+ import { createPost } from './actions';
134
+
135
+ export function NewPostForm() {
136
+ return (
137
+ <form action={createPost}>
138
+ <input name="title" />
139
+ <button type="submit">Create</button>
140
+ </form>
141
+ );
142
+ }
143
+ ```
144
+
145
+ ---
146
+
147
+ ## 6. Caching Layers (Next.js 16+)
148
+
149
+ 1. **React `cache()`** — per-request memoization
150
+ 2. **`unstable_cache`** — shared across requests (with tags)
151
+ 3. **Route segment config** — `export const revalidate = 3600`
152
+ 4. **Dynamic functions** (`cookies()`, `headers()`) — opt out of static rendering
153
+
154
+ ---
155
+
156
+ ## 7. Common Pitfalls in 2026
157
+
158
+ | Mistake | Fix |
159
+ |---------|-----|
160
+ | Putting `'use client'` at the root layout | Only add it to interactive leaves |
161
+ | Passing functions or class instances as props | Serialize on the server first |
162
+ | Sequential `await` in Server Components | Use `Promise.all` |
163
+ | Using Context at the root layout | Context only works inside Client Components |
164
+ | Forgetting to handle loading states with Suspense | Wrap slow sections in `<Suspense>` |
165
+ | Using `Date` objects directly across boundary | Convert to ISO string on the server |
166
+
167
+ ---
168
+
169
+ ## 8. When to Use Client Components
170
+
171
+ Only when you need:
172
+
173
+ - `useState`, `useEffect`, `useReducer`, `useContext`
174
+ - Browser APIs (`localStorage`, `window`, `document`)
175
+ - Event handlers (`onClick`, `onSubmit`)
176
+ - Third-party libraries that require the browser (many chart libs, drag-and-drop, etc.)
177
+
178
+ ---
179
+
180
+ ## See Also
181
+
182
+ - `nextjs-app-router` — framework-specific patterns on top of RSC
183
+ - `react-patterns` — general React 19 best practices
184
+ - Official React docs: https://react.dev/reference/rsc/server-components
185
+
186
+ ---
187
+
188
+ ## Memory Optimization Trigger
189
+
190
+ If this skill accumulates many near-duplicate examples or grows beyond ~200 lines, run:
191
+
192
+ ```bash
193
+ npx start-vibing-stacks memory optimize --dry-run
194
+ ```
@@ -81,7 +81,8 @@
81
81
  "icon": "⚛️",
82
82
  "skillsDir": "react",
83
83
  "default": true,
84
- "frameworks": ["nextjs", "express", "fastify", "vanilla"]
84
+ "frameworks": ["nextjs", "express", "fastify", "vanilla"],
85
+ "skills": ["react-server-components"]
85
86
  },
86
87
  {
87
88
  "id": "vue",
@@ -109,7 +110,9 @@
109
110
  "bun-runtime",
110
111
  "zod-validation",
111
112
  "api-security-node",
112
- "openapi-design"
113
+ "openapi-design",
114
+ "docker-patterns",
115
+ "podman-patterns"
113
116
  ],
114
117
  "requirements": [
115
118
  {
@@ -33,7 +33,8 @@
33
33
  "laravel-patterns",
34
34
  "laravel-octane",
35
35
  "laravel-api-architecture",
36
- "api-security"
36
+ "api-security",
37
+ "laravel-octane-inertia"
37
38
  ]
38
39
  },
39
40
  {
@@ -44,7 +45,8 @@
44
45
  "skills": [
45
46
  "laravel-patterns",
46
47
  "laravel-api-architecture",
47
- "api-security"
48
+ "api-security",
49
+ "laravel-octane-inertia"
48
50
  ]
49
51
  }
50
52
  ],
@@ -98,7 +100,9 @@
98
100
  "api-design",
99
101
  "api-security",
100
102
  "laravel-api-architecture",
101
- "openapi-design"
103
+ "openapi-design",
104
+ "docker-patterns",
105
+ "podman-patterns"
102
106
  ],
103
107
  "requirements": [
104
108
  {
@@ -70,7 +70,9 @@
70
70
  "pydantic-validation",
71
71
  "pytest-testing",
72
72
  "python-performance",
73
- "api-security-python"
73
+ "api-security-python",
74
+ "docker-patterns",
75
+ "podman-patterns"
74
76
  ],
75
77
  "requirements": [
76
78
  {