@venizia/ignis-docs 0.0.3 → 0.0.4-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.
- package/README.md +1 -1
- package/package.json +4 -2
- package/wiki/best-practices/api-usage-examples.md +591 -0
- package/wiki/best-practices/architectural-patterns.md +415 -0
- package/wiki/best-practices/architecture-decisions.md +488 -0
- package/wiki/{get-started/best-practices → best-practices}/code-style-standards.md +406 -17
- package/wiki/{get-started/best-practices → best-practices}/common-pitfalls.md +109 -4
- package/wiki/{get-started/best-practices → best-practices}/contribution-workflow.md +34 -7
- package/wiki/best-practices/data-modeling.md +376 -0
- package/wiki/best-practices/deployment-strategies.md +698 -0
- package/wiki/best-practices/index.md +27 -0
- package/wiki/best-practices/performance-optimization.md +196 -0
- package/wiki/best-practices/security-guidelines.md +218 -0
- package/wiki/{get-started/best-practices → best-practices}/troubleshooting-tips.md +97 -1
- package/wiki/changelogs/2025-12-16-initial-architecture.md +1 -1
- package/wiki/changelogs/2025-12-16-model-repo-datasource-refactor.md +1 -1
- package/wiki/changelogs/2025-12-17-refactor.md +1 -1
- package/wiki/changelogs/2025-12-18-performance-optimizations.md +5 -5
- package/wiki/changelogs/2025-12-18-repository-validation-security.md +13 -7
- package/wiki/changelogs/2025-12-26-nested-relations-and-generics.md +2 -2
- package/wiki/changelogs/2025-12-29-dynamic-binding-registration.md +104 -0
- package/wiki/changelogs/2025-12-29-snowflake-uid-helper.md +100 -0
- package/wiki/changelogs/2025-12-30-repository-enhancements.md +214 -0
- package/wiki/changelogs/2025-12-31-json-path-filtering-array-operators.md +214 -0
- package/wiki/changelogs/2025-12-31-string-id-custom-generator.md +137 -0
- package/wiki/changelogs/2026-01-02-default-filter-and-repository-mixins.md +418 -0
- package/wiki/changelogs/index.md +6 -0
- package/wiki/changelogs/planned-schema-migrator.md +0 -8
- package/wiki/{get-started/core-concepts → guides/core-concepts/application}/bootstrapping.md +18 -5
- package/wiki/{get-started/core-concepts/application.md → guides/core-concepts/application/index.md} +47 -104
- package/wiki/guides/core-concepts/components-guide.md +509 -0
- package/wiki/{get-started → guides}/core-concepts/components.md +24 -17
- package/wiki/{get-started → guides}/core-concepts/controllers.md +30 -13
- package/wiki/{get-started → guides}/core-concepts/dependency-injection.md +97 -0
- package/wiki/guides/core-concepts/persistent/datasources.md +179 -0
- package/wiki/guides/core-concepts/persistent/index.md +119 -0
- package/wiki/guides/core-concepts/persistent/models.md +241 -0
- package/wiki/guides/core-concepts/persistent/repositories.md +219 -0
- package/wiki/guides/core-concepts/persistent/transactions.md +170 -0
- package/wiki/{get-started → guides}/core-concepts/services.md +26 -3
- package/wiki/{get-started → guides/get-started}/5-minute-quickstart.md +59 -14
- package/wiki/guides/get-started/philosophy.md +682 -0
- package/wiki/guides/get-started/setup.md +157 -0
- package/wiki/guides/index.md +89 -0
- package/wiki/guides/reference/glossary.md +243 -0
- package/wiki/{get-started → guides/reference}/mcp-docs-server.md +0 -10
- package/wiki/{get-started → guides/tutorials}/building-a-crud-api.md +134 -132
- package/wiki/{get-started/quickstart.md → guides/tutorials/complete-installation.md} +107 -71
- package/wiki/guides/tutorials/ecommerce-api.md +1399 -0
- package/wiki/guides/tutorials/realtime-chat.md +1261 -0
- package/wiki/guides/tutorials/testing.md +723 -0
- package/wiki/index.md +176 -37
- package/wiki/references/base/application.md +27 -0
- package/wiki/references/base/bootstrapping.md +30 -26
- package/wiki/references/base/components.md +24 -7
- package/wiki/references/base/controllers.md +51 -20
- package/wiki/references/base/datasources.md +30 -0
- package/wiki/references/base/dependency-injection.md +39 -3
- package/wiki/references/base/filter-system/application-usage.md +224 -0
- package/wiki/references/base/filter-system/array-operators.md +132 -0
- package/wiki/references/base/filter-system/comparison-operators.md +109 -0
- package/wiki/references/base/filter-system/default-filter.md +428 -0
- package/wiki/references/base/filter-system/fields-order-pagination.md +155 -0
- package/wiki/references/base/filter-system/index.md +127 -0
- package/wiki/references/base/filter-system/json-filtering.md +197 -0
- package/wiki/references/base/filter-system/list-operators.md +71 -0
- package/wiki/references/base/filter-system/logical-operators.md +156 -0
- package/wiki/references/base/filter-system/null-operators.md +58 -0
- package/wiki/references/base/filter-system/pattern-matching.md +108 -0
- package/wiki/references/base/filter-system/quick-reference.md +431 -0
- package/wiki/references/base/filter-system/range-operators.md +63 -0
- package/wiki/references/base/filter-system/tips.md +190 -0
- package/wiki/references/base/filter-system/use-cases.md +452 -0
- package/wiki/references/base/index.md +90 -0
- package/wiki/references/base/middlewares.md +602 -0
- package/wiki/references/base/models.md +215 -23
- package/wiki/references/base/providers.md +732 -0
- package/wiki/references/base/repositories/advanced.md +555 -0
- package/wiki/references/base/repositories/index.md +228 -0
- package/wiki/references/base/repositories/mixins.md +331 -0
- package/wiki/references/base/repositories/relations.md +486 -0
- package/wiki/references/base/repositories.md +40 -635
- package/wiki/references/base/services.md +28 -4
- package/wiki/references/components/authentication.md +22 -2
- package/wiki/references/components/health-check.md +12 -0
- package/wiki/references/components/index.md +23 -0
- package/wiki/references/components/mail.md +687 -0
- package/wiki/references/components/request-tracker.md +16 -0
- package/wiki/references/components/socket-io.md +18 -0
- package/wiki/references/components/static-asset.md +14 -26
- package/wiki/references/components/swagger.md +17 -0
- package/wiki/references/configuration/environment-variables.md +427 -0
- package/wiki/references/configuration/index.md +73 -0
- package/wiki/references/helpers/cron.md +14 -0
- package/wiki/references/helpers/crypto.md +15 -0
- package/wiki/references/helpers/env.md +16 -0
- package/wiki/references/helpers/error.md +17 -0
- package/wiki/references/helpers/index.md +14 -0
- package/wiki/references/helpers/inversion.md +24 -4
- package/wiki/references/helpers/logger.md +19 -0
- package/wiki/references/helpers/network.md +11 -0
- package/wiki/references/helpers/queue.md +19 -0
- package/wiki/references/helpers/redis.md +21 -0
- package/wiki/references/helpers/socket-io.md +24 -5
- package/wiki/references/helpers/storage.md +18 -10
- package/wiki/references/helpers/testing.md +18 -0
- package/wiki/references/helpers/types.md +16 -0
- package/wiki/references/helpers/uid.md +167 -0
- package/wiki/references/helpers/worker-thread.md +16 -0
- package/wiki/references/index.md +177 -0
- package/wiki/references/quick-reference.md +634 -0
- package/wiki/references/src-details/boot.md +3 -3
- package/wiki/references/src-details/dev-configs.md +0 -4
- package/wiki/references/src-details/docs.md +2 -2
- package/wiki/references/src-details/index.md +86 -0
- package/wiki/references/src-details/inversion.md +1 -6
- package/wiki/references/src-details/mcp-server.md +3 -15
- package/wiki/references/utilities/index.md +86 -10
- package/wiki/references/utilities/jsx.md +577 -0
- package/wiki/references/utilities/request.md +0 -2
- package/wiki/references/utilities/statuses.md +740 -0
- package/wiki/get-started/best-practices/api-usage-examples.md +0 -266
- package/wiki/get-started/best-practices/architectural-patterns.md +0 -170
- package/wiki/get-started/best-practices/data-modeling.md +0 -177
- package/wiki/get-started/best-practices/deployment-strategies.md +0 -121
- package/wiki/get-started/best-practices/performance-optimization.md +0 -97
- package/wiki/get-started/best-practices/security-guidelines.md +0 -99
- package/wiki/get-started/core-concepts/persistent.md +0 -539
- package/wiki/get-started/index.md +0 -65
- package/wiki/get-started/philosophy.md +0 -296
- package/wiki/get-started/prerequisites.md +0 -113
|
@@ -0,0 +1,698 @@
|
|
|
1
|
+
# Deployment Strategies
|
|
2
|
+
|
|
3
|
+
Deploy your Ignis application reliably, securely, and efficiently.
|
|
4
|
+
|
|
5
|
+
## 1. Building for Production
|
|
6
|
+
|
|
7
|
+
Compile TypeScript to JavaScript before deploying:
|
|
8
|
+
|
|
9
|
+
```bash
|
|
10
|
+
bun run build
|
|
11
|
+
```
|
|
12
|
+
|
|
13
|
+
**What this does:**
|
|
14
|
+
1. `tsc -p tsconfig.json` - Compile TypeScript → JavaScript
|
|
15
|
+
2. `tsc-alias -p tsconfig.json` - Replace path aliases (`@/*`) with relative paths
|
|
16
|
+
|
|
17
|
+
**Output:** `dist/` folder with production-ready JavaScript.
|
|
18
|
+
|
|
19
|
+
## 2. Environment Configuration
|
|
20
|
+
|
|
21
|
+
Use environment variables for all configuration - never hard-code.
|
|
22
|
+
|
|
23
|
+
**Production Environment Variables:**
|
|
24
|
+
| Variable | Value | Purpose |
|
|
25
|
+
|----------|-------|---------|
|
|
26
|
+
| `NODE_ENV` | `production` | Enables performance optimizations |
|
|
27
|
+
| `APP_ENV_APPLICATION_SECRET` | Strong random string | Application secret |
|
|
28
|
+
| `APP_ENV_JWT_SECRET` | Strong random string | JWT signing key |
|
|
29
|
+
| `APP_ENV_POSTGRES_*` | Production DB credentials | Database connection |
|
|
30
|
+
| `APP_ENV_SERVER_HOST` | `0.0.0.0` | Accept connections from any IP |
|
|
31
|
+
| `APP_ENV_SERVER_PORT` | `3000` or cloud-assigned | Server port |
|
|
32
|
+
|
|
33
|
+
**Where to store:**
|
|
34
|
+
- **Docker:** Use environment variables in `docker-compose.yml` or secrets
|
|
35
|
+
- **Kubernetes:** ConfigMaps and Secrets
|
|
36
|
+
- **Cloud Platforms:** AWS Secrets Manager, Azure Key Vault, Google Secret Manager
|
|
37
|
+
|
|
38
|
+
## 3. Deployment Methods
|
|
39
|
+
|
|
40
|
+
### Docker Deployment (Recommended)
|
|
41
|
+
|
|
42
|
+
**Dockerfile:**
|
|
43
|
+
```dockerfile
|
|
44
|
+
FROM oven/bun:1-slim
|
|
45
|
+
|
|
46
|
+
WORKDIR /usr/src/app
|
|
47
|
+
|
|
48
|
+
# Copy dependency files
|
|
49
|
+
COPY package.json bun.lockb ./
|
|
50
|
+
|
|
51
|
+
# Install production dependencies
|
|
52
|
+
RUN bun install --production --frozen-lockfile
|
|
53
|
+
|
|
54
|
+
# Copy source code
|
|
55
|
+
COPY . .
|
|
56
|
+
|
|
57
|
+
# Build TypeScript
|
|
58
|
+
RUN bun run build
|
|
59
|
+
|
|
60
|
+
# Expose port
|
|
61
|
+
EXPOSE 3000
|
|
62
|
+
|
|
63
|
+
# Start server
|
|
64
|
+
CMD [ "bun", "run", "server:prod" ]
|
|
65
|
+
```
|
|
66
|
+
|
|
67
|
+
**Build and deploy:**
|
|
68
|
+
```bash
|
|
69
|
+
# Build image
|
|
70
|
+
docker build -t my-ignis-app .
|
|
71
|
+
|
|
72
|
+
# Run container
|
|
73
|
+
docker run -p 3000:3000 \
|
|
74
|
+
-e NODE_ENV=production \
|
|
75
|
+
-e APP_ENV_APPLICATION_SECRET=xxx \
|
|
76
|
+
my-ignis-app
|
|
77
|
+
```
|
|
78
|
+
|
|
79
|
+
### Docker Compose (Full Stack)
|
|
80
|
+
|
|
81
|
+
For complete development and staging environments with database:
|
|
82
|
+
|
|
83
|
+
**docker-compose.yml:**
|
|
84
|
+
```yaml
|
|
85
|
+
version: '3.8'
|
|
86
|
+
|
|
87
|
+
services:
|
|
88
|
+
app:
|
|
89
|
+
build:
|
|
90
|
+
context: .
|
|
91
|
+
dockerfile: Dockerfile
|
|
92
|
+
ports:
|
|
93
|
+
- "3000:3000"
|
|
94
|
+
environment:
|
|
95
|
+
- NODE_ENV=production
|
|
96
|
+
- APP_ENV_APPLICATION_SECRET=${APP_SECRET}
|
|
97
|
+
- APP_ENV_JWT_SECRET=${JWT_SECRET}
|
|
98
|
+
- APP_ENV_POSTGRES_HOST=db
|
|
99
|
+
- APP_ENV_POSTGRES_PORT=5432
|
|
100
|
+
- APP_ENV_POSTGRES_USERNAME=ignis
|
|
101
|
+
- APP_ENV_POSTGRES_PASSWORD=${DB_PASSWORD}
|
|
102
|
+
- APP_ENV_POSTGRES_DATABASE=ignis_db
|
|
103
|
+
- APP_ENV_REDIS_HOST=redis
|
|
104
|
+
- APP_ENV_REDIS_PORT=6379
|
|
105
|
+
depends_on:
|
|
106
|
+
db:
|
|
107
|
+
condition: service_healthy
|
|
108
|
+
redis:
|
|
109
|
+
condition: service_started
|
|
110
|
+
restart: unless-stopped
|
|
111
|
+
healthcheck:
|
|
112
|
+
test: ["CMD", "curl", "-f", "http://localhost:3000/health-check"]
|
|
113
|
+
interval: 30s
|
|
114
|
+
timeout: 10s
|
|
115
|
+
retries: 3
|
|
116
|
+
|
|
117
|
+
db:
|
|
118
|
+
image: postgres:16-alpine
|
|
119
|
+
environment:
|
|
120
|
+
- POSTGRES_USER=ignis
|
|
121
|
+
- POSTGRES_PASSWORD=${DB_PASSWORD}
|
|
122
|
+
- POSTGRES_DB=ignis_db
|
|
123
|
+
volumes:
|
|
124
|
+
- postgres_data:/var/lib/postgresql/data
|
|
125
|
+
healthcheck:
|
|
126
|
+
test: ["CMD-SHELL", "pg_isready -U ignis -d ignis_db"]
|
|
127
|
+
interval: 10s
|
|
128
|
+
timeout: 5s
|
|
129
|
+
retries: 5
|
|
130
|
+
|
|
131
|
+
redis:
|
|
132
|
+
image: redis:7-alpine
|
|
133
|
+
command: redis-server --appendonly yes
|
|
134
|
+
volumes:
|
|
135
|
+
- redis_data:/data
|
|
136
|
+
|
|
137
|
+
volumes:
|
|
138
|
+
postgres_data:
|
|
139
|
+
redis_data:
|
|
140
|
+
```
|
|
141
|
+
|
|
142
|
+
**Deploy with docker-compose:**
|
|
143
|
+
```bash
|
|
144
|
+
# Create .env file with secrets
|
|
145
|
+
echo "APP_SECRET=$(openssl rand -base64 32)" > .env
|
|
146
|
+
echo "JWT_SECRET=$(openssl rand -base64 32)" >> .env
|
|
147
|
+
echo "DB_PASSWORD=$(openssl rand -base64 24)" >> .env
|
|
148
|
+
|
|
149
|
+
# Start all services
|
|
150
|
+
docker-compose up -d
|
|
151
|
+
|
|
152
|
+
# View logs
|
|
153
|
+
docker-compose logs -f app
|
|
154
|
+
|
|
155
|
+
# Scale app (for load testing)
|
|
156
|
+
docker-compose up -d --scale app=3
|
|
157
|
+
```
|
|
158
|
+
|
|
159
|
+
### Bun Single Executable (Alternative)
|
|
160
|
+
|
|
161
|
+
Compile your app into a single standalone binary:
|
|
162
|
+
|
|
163
|
+
```bash
|
|
164
|
+
bun build --compile --minify --target=bun-linux-x64 \
|
|
165
|
+
./src/index.ts --outfile ./dist/my-app
|
|
166
|
+
```
|
|
167
|
+
|
|
168
|
+
**Pros:** No dependencies needed on server, simple deployment
|
|
169
|
+
**Cons:** Platform-specific, newer technology (test thoroughly)
|
|
170
|
+
|
|
171
|
+
**Deploy:**
|
|
172
|
+
```bash
|
|
173
|
+
# Copy executable and .env to server
|
|
174
|
+
scp dist/my-app .env user@server:/app/
|
|
175
|
+
|
|
176
|
+
# Run
|
|
177
|
+
./my-app
|
|
178
|
+
```
|
|
179
|
+
|
|
180
|
+
## 4. Production Best Practices
|
|
181
|
+
|
|
182
|
+
**Use a process manager:**
|
|
183
|
+
- **systemd** - Linux service management (recommended for Bun)
|
|
184
|
+
- **Docker/Kubernetes** - Built-in orchestration
|
|
185
|
+
- **PM2** - Alternative option
|
|
186
|
+
|
|
187
|
+
**Example with systemd (Recommended for Bun):**
|
|
188
|
+
```ini
|
|
189
|
+
# /etc/systemd/system/my-app.service
|
|
190
|
+
[Unit]
|
|
191
|
+
Description=My Ignis Application
|
|
192
|
+
After=network.target
|
|
193
|
+
|
|
194
|
+
[Service]
|
|
195
|
+
Type=simple
|
|
196
|
+
User=www-data
|
|
197
|
+
WorkingDirectory=/app
|
|
198
|
+
ExecStart=/usr/local/bin/bun run server:prod
|
|
199
|
+
Restart=on-failure
|
|
200
|
+
RestartSec=10
|
|
201
|
+
Environment=NODE_ENV=production
|
|
202
|
+
|
|
203
|
+
[Install]
|
|
204
|
+
WantedBy=multi-user.target
|
|
205
|
+
```
|
|
206
|
+
|
|
207
|
+
```bash
|
|
208
|
+
# Enable and start the service
|
|
209
|
+
sudo systemctl enable my-app
|
|
210
|
+
sudo systemctl start my-app
|
|
211
|
+
sudo systemctl status my-app
|
|
212
|
+
```
|
|
213
|
+
|
|
214
|
+
**Example with PM2 (Alternative):**
|
|
215
|
+
```bash
|
|
216
|
+
pm2 start "bun run server:prod" --name my-app
|
|
217
|
+
pm2 save
|
|
218
|
+
pm2 startup
|
|
219
|
+
```
|
|
220
|
+
|
|
221
|
+
**Health checks:**
|
|
222
|
+
Add health check endpoint for load balancers:
|
|
223
|
+
```typescript
|
|
224
|
+
// In application.ts
|
|
225
|
+
this.component(HealthCheckComponent);
|
|
226
|
+
```
|
|
227
|
+
|
|
228
|
+
Access at `/health-check` for liveness/readiness probes.
|
|
229
|
+
|
|
230
|
+
## 5. Build Debugging
|
|
231
|
+
|
|
232
|
+
When builds fail or behave unexpectedly, use TypeScript's extended diagnostics:
|
|
233
|
+
|
|
234
|
+
```bash
|
|
235
|
+
# Show detailed build timing and statistics
|
|
236
|
+
tsc -p tsconfig.json --extendedDiagnostics
|
|
237
|
+
```
|
|
238
|
+
|
|
239
|
+
**Output includes:**
|
|
240
|
+
- File I/O time
|
|
241
|
+
- Parse time
|
|
242
|
+
- Program time
|
|
243
|
+
- Bind time
|
|
244
|
+
- Check time
|
|
245
|
+
- Emit time
|
|
246
|
+
- Total time
|
|
247
|
+
|
|
248
|
+
**Example output:**
|
|
249
|
+
```
|
|
250
|
+
Files: 245
|
|
251
|
+
Lines: 89432
|
|
252
|
+
Nodes: 412856
|
|
253
|
+
Identifiers: 156234
|
|
254
|
+
Symbols: 98765
|
|
255
|
+
Types: 34567
|
|
256
|
+
Instantiations: 123456
|
|
257
|
+
Memory used: 245678K
|
|
258
|
+
I/O Read time: 0.23s
|
|
259
|
+
Parse time: 1.45s
|
|
260
|
+
Program time: 2.34s
|
|
261
|
+
Bind time: 0.56s
|
|
262
|
+
Check time: 4.23s
|
|
263
|
+
Emit time: 0.89s
|
|
264
|
+
Total time: 8.47s
|
|
265
|
+
```
|
|
266
|
+
|
|
267
|
+
**Common issues:**
|
|
268
|
+
- High "Check time" → Type errors or complex type inference
|
|
269
|
+
- High "I/O Read time" → Too many files, check `include`/`exclude` patterns
|
|
270
|
+
- High "Instantiations" → Complex generic types, consider simplifying
|
|
271
|
+
|
|
272
|
+
## 6. Dependency Management
|
|
273
|
+
|
|
274
|
+
### Force Update Strategy
|
|
275
|
+
|
|
276
|
+
Keep dependencies in sync with the NPM registry using the force-update script:
|
|
277
|
+
|
|
278
|
+
```bash
|
|
279
|
+
# Update to latest stable versions
|
|
280
|
+
./scripts/force-update.sh latest
|
|
281
|
+
|
|
282
|
+
# Update to pre-release versions (for testing new features)
|
|
283
|
+
./scripts/force-update.sh next
|
|
284
|
+
```
|
|
285
|
+
|
|
286
|
+
**What it does:**
|
|
287
|
+
1. Queries NPM registry for the specified tag (`latest` or `next`)
|
|
288
|
+
2. Updates `package.json` with exact versions
|
|
289
|
+
3. Applies to all `@venizia/*` packages
|
|
290
|
+
|
|
291
|
+
**When to use:**
|
|
292
|
+
| Tag | Use Case |
|
|
293
|
+
|-----|----------|
|
|
294
|
+
| `latest` | Production deployments, stable releases |
|
|
295
|
+
| `next` | Testing new features, pre-release validation |
|
|
296
|
+
|
|
297
|
+
**Makefile shortcuts:**
|
|
298
|
+
```bash
|
|
299
|
+
make update # Force update all packages (latest)
|
|
300
|
+
make update-core # Update only @venizia/ignis
|
|
301
|
+
make update-helpers # Update only @venizia/ignis-helpers
|
|
302
|
+
```
|
|
303
|
+
|
|
304
|
+
## 7. Test Environment Setup
|
|
305
|
+
|
|
306
|
+
Configure separate environment for testing:
|
|
307
|
+
|
|
308
|
+
### Create `.env.test`
|
|
309
|
+
|
|
310
|
+
```bash
|
|
311
|
+
# .env.test - Test environment variables
|
|
312
|
+
NODE_ENV=test
|
|
313
|
+
APP_ENV_APPLICATION_SECRET=test-secret-key
|
|
314
|
+
APP_ENV_JWT_SECRET=test-jwt-secret
|
|
315
|
+
APP_ENV_POSTGRES_HOST=localhost
|
|
316
|
+
APP_ENV_POSTGRES_PORT=5433
|
|
317
|
+
APP_ENV_POSTGRES_USERNAME=test_user
|
|
318
|
+
APP_ENV_POSTGRES_PASSWORD=test_password
|
|
319
|
+
APP_ENV_POSTGRES_DATABASE=test_db
|
|
320
|
+
```
|
|
321
|
+
|
|
322
|
+
### Running Tests
|
|
323
|
+
|
|
324
|
+
```bash
|
|
325
|
+
# Run all tests with test environment
|
|
326
|
+
NODE_ENV=test bun test --env-file=.env.test
|
|
327
|
+
|
|
328
|
+
# Run tests in watch mode
|
|
329
|
+
NODE_ENV=test bun test --watch --env-file=.env.test
|
|
330
|
+
|
|
331
|
+
# Run specific test file
|
|
332
|
+
NODE_ENV=test bun test --env-file=.env.test src/__tests__/user.test.ts
|
|
333
|
+
```
|
|
334
|
+
|
|
335
|
+
### Test Database Setup
|
|
336
|
+
|
|
337
|
+
For integration tests, use a separate database:
|
|
338
|
+
|
|
339
|
+
```bash
|
|
340
|
+
# Docker: Start test database
|
|
341
|
+
docker run -d \
|
|
342
|
+
--name ignis-test-db \
|
|
343
|
+
-e POSTGRES_USER=test_user \
|
|
344
|
+
-e POSTGRES_PASSWORD=test_password \
|
|
345
|
+
-e POSTGRES_DB=test_db \
|
|
346
|
+
-p 5433:5432 \
|
|
347
|
+
postgres:16
|
|
348
|
+
|
|
349
|
+
# Run migrations on test database
|
|
350
|
+
NODE_ENV=test bun run migrate --env-file=.env.test
|
|
351
|
+
```
|
|
352
|
+
|
|
353
|
+
## 8. CI/CD Security
|
|
354
|
+
|
|
355
|
+
### Dependency Auditing
|
|
356
|
+
|
|
357
|
+
Integrate security audits into your CI/CD pipeline:
|
|
358
|
+
|
|
359
|
+
```yaml
|
|
360
|
+
# GitHub Actions example
|
|
361
|
+
name: Security Audit
|
|
362
|
+
|
|
363
|
+
on:
|
|
364
|
+
push:
|
|
365
|
+
branches: [main, develop]
|
|
366
|
+
pull_request:
|
|
367
|
+
branches: [main]
|
|
368
|
+
schedule:
|
|
369
|
+
- cron: '0 0 * * 1' # Weekly on Monday
|
|
370
|
+
|
|
371
|
+
jobs:
|
|
372
|
+
audit:
|
|
373
|
+
runs-on: ubuntu-latest
|
|
374
|
+
steps:
|
|
375
|
+
- uses: actions/checkout@v4
|
|
376
|
+
|
|
377
|
+
- uses: oven-sh/setup-bun@v2
|
|
378
|
+
with:
|
|
379
|
+
bun-version: latest
|
|
380
|
+
|
|
381
|
+
- name: Install dependencies
|
|
382
|
+
run: bun install
|
|
383
|
+
|
|
384
|
+
- name: Run security audit
|
|
385
|
+
run: bun audit
|
|
386
|
+
|
|
387
|
+
- name: Check for vulnerabilities
|
|
388
|
+
run: |
|
|
389
|
+
if bun audit --json | jq '.vulnerabilities | length' | grep -v '^0$'; then
|
|
390
|
+
echo "Vulnerabilities found!"
|
|
391
|
+
exit 1
|
|
392
|
+
fi
|
|
393
|
+
```
|
|
394
|
+
|
|
395
|
+
### Pre-deployment Checklist
|
|
396
|
+
|
|
397
|
+
```yaml
|
|
398
|
+
# GitHub Actions - Full CI pipeline
|
|
399
|
+
jobs:
|
|
400
|
+
build-and-test:
|
|
401
|
+
runs-on: ubuntu-latest
|
|
402
|
+
steps:
|
|
403
|
+
- uses: actions/checkout@v4
|
|
404
|
+
- uses: oven-sh/setup-bun@v2
|
|
405
|
+
|
|
406
|
+
- name: Install
|
|
407
|
+
run: bun install
|
|
408
|
+
|
|
409
|
+
- name: Lint
|
|
410
|
+
run: bun run lint
|
|
411
|
+
|
|
412
|
+
- name: Build
|
|
413
|
+
run: bun run build
|
|
414
|
+
|
|
415
|
+
- name: Test
|
|
416
|
+
run: bun test --env-file=.env.test
|
|
417
|
+
|
|
418
|
+
- name: Security Audit
|
|
419
|
+
run: bun audit
|
|
420
|
+
|
|
421
|
+
- name: Build Docker Image
|
|
422
|
+
run: docker build -t my-app:${{ github.sha }} .
|
|
423
|
+
```
|
|
424
|
+
|
|
425
|
+
### Critical Packages to Monitor
|
|
426
|
+
|
|
427
|
+
| Package | Why | Check |
|
|
428
|
+
|---------|-----|-------|
|
|
429
|
+
| `hono` | Web framework, HTTP handling | Security advisories |
|
|
430
|
+
| `drizzle-orm` | Database queries, SQL injection | Version updates |
|
|
431
|
+
| `jose` | JWT handling, crypto | Vulnerability patches |
|
|
432
|
+
| `@venizia/ignis` | Framework core | Latest stable release |
|
|
433
|
+
|
|
434
|
+
## 9. Cloud Platform Deployments
|
|
435
|
+
|
|
436
|
+
### Railway
|
|
437
|
+
|
|
438
|
+
Railway provides simple deployments with automatic builds:
|
|
439
|
+
|
|
440
|
+
**railway.json:**
|
|
441
|
+
```json
|
|
442
|
+
{
|
|
443
|
+
"$schema": "https://railway.app/railway.schema.json",
|
|
444
|
+
"build": {
|
|
445
|
+
"builder": "DOCKERFILE",
|
|
446
|
+
"dockerfilePath": "Dockerfile"
|
|
447
|
+
},
|
|
448
|
+
"deploy": {
|
|
449
|
+
"startCommand": "bun run server:prod",
|
|
450
|
+
"healthcheckPath": "/health-check",
|
|
451
|
+
"healthcheckTimeout": 30,
|
|
452
|
+
"restartPolicyType": "ON_FAILURE",
|
|
453
|
+
"restartPolicyMaxRetries": 3
|
|
454
|
+
}
|
|
455
|
+
}
|
|
456
|
+
```
|
|
457
|
+
|
|
458
|
+
```bash
|
|
459
|
+
# Deploy to Railway
|
|
460
|
+
railway login
|
|
461
|
+
railway init
|
|
462
|
+
railway up
|
|
463
|
+
```
|
|
464
|
+
|
|
465
|
+
### Fly.io
|
|
466
|
+
|
|
467
|
+
**fly.toml:**
|
|
468
|
+
```toml
|
|
469
|
+
app = "my-ignis-app"
|
|
470
|
+
primary_region = "sjc"
|
|
471
|
+
|
|
472
|
+
[build]
|
|
473
|
+
dockerfile = "Dockerfile"
|
|
474
|
+
|
|
475
|
+
[http_service]
|
|
476
|
+
internal_port = 3000
|
|
477
|
+
force_https = true
|
|
478
|
+
auto_stop_machines = true
|
|
479
|
+
auto_start_machines = true
|
|
480
|
+
min_machines_running = 1
|
|
481
|
+
|
|
482
|
+
[[services]]
|
|
483
|
+
protocol = "tcp"
|
|
484
|
+
internal_port = 3000
|
|
485
|
+
|
|
486
|
+
[[services.ports]]
|
|
487
|
+
port = 80
|
|
488
|
+
handlers = ["http"]
|
|
489
|
+
|
|
490
|
+
[[services.ports]]
|
|
491
|
+
port = 443
|
|
492
|
+
handlers = ["tls", "http"]
|
|
493
|
+
|
|
494
|
+
[[services.http_checks]]
|
|
495
|
+
interval = 10000
|
|
496
|
+
grace_period = "5s"
|
|
497
|
+
method = "get"
|
|
498
|
+
path = "/health-check"
|
|
499
|
+
protocol = "http"
|
|
500
|
+
timeout = 2000
|
|
501
|
+
```
|
|
502
|
+
|
|
503
|
+
```bash
|
|
504
|
+
# Deploy to Fly.io
|
|
505
|
+
fly auth login
|
|
506
|
+
fly launch
|
|
507
|
+
fly deploy
|
|
508
|
+
fly secrets set APP_ENV_APPLICATION_SECRET=xxx
|
|
509
|
+
```
|
|
510
|
+
|
|
511
|
+
### Render
|
|
512
|
+
|
|
513
|
+
**render.yaml:**
|
|
514
|
+
```yaml
|
|
515
|
+
services:
|
|
516
|
+
- type: web
|
|
517
|
+
name: my-ignis-app
|
|
518
|
+
runtime: docker
|
|
519
|
+
dockerfilePath: ./Dockerfile
|
|
520
|
+
envVars:
|
|
521
|
+
- key: NODE_ENV
|
|
522
|
+
value: production
|
|
523
|
+
- key: APP_ENV_APPLICATION_SECRET
|
|
524
|
+
generateValue: true
|
|
525
|
+
- key: APP_ENV_JWT_SECRET
|
|
526
|
+
generateValue: true
|
|
527
|
+
healthCheckPath: /health-check
|
|
528
|
+
autoDeploy: true
|
|
529
|
+
|
|
530
|
+
databases:
|
|
531
|
+
- name: ignis-db
|
|
532
|
+
databaseName: ignis
|
|
533
|
+
user: ignis
|
|
534
|
+
plan: starter
|
|
535
|
+
```
|
|
536
|
+
|
|
537
|
+
### Kubernetes
|
|
538
|
+
|
|
539
|
+
**k8s/deployment.yaml:**
|
|
540
|
+
```yaml
|
|
541
|
+
apiVersion: apps/v1
|
|
542
|
+
kind: Deployment
|
|
543
|
+
metadata:
|
|
544
|
+
name: ignis-app
|
|
545
|
+
labels:
|
|
546
|
+
app: ignis
|
|
547
|
+
spec:
|
|
548
|
+
replicas: 3
|
|
549
|
+
selector:
|
|
550
|
+
matchLabels:
|
|
551
|
+
app: ignis
|
|
552
|
+
template:
|
|
553
|
+
metadata:
|
|
554
|
+
labels:
|
|
555
|
+
app: ignis
|
|
556
|
+
spec:
|
|
557
|
+
containers:
|
|
558
|
+
- name: ignis
|
|
559
|
+
image: my-ignis-app:latest
|
|
560
|
+
ports:
|
|
561
|
+
- containerPort: 3000
|
|
562
|
+
env:
|
|
563
|
+
- name: NODE_ENV
|
|
564
|
+
value: "production"
|
|
565
|
+
- name: APP_ENV_APPLICATION_SECRET
|
|
566
|
+
valueFrom:
|
|
567
|
+
secretKeyRef:
|
|
568
|
+
name: ignis-secrets
|
|
569
|
+
key: app-secret
|
|
570
|
+
- name: APP_ENV_JWT_SECRET
|
|
571
|
+
valueFrom:
|
|
572
|
+
secretKeyRef:
|
|
573
|
+
name: ignis-secrets
|
|
574
|
+
key: jwt-secret
|
|
575
|
+
- name: APP_ENV_POSTGRES_HOST
|
|
576
|
+
valueFrom:
|
|
577
|
+
configMapKeyRef:
|
|
578
|
+
name: ignis-config
|
|
579
|
+
key: db-host
|
|
580
|
+
livenessProbe:
|
|
581
|
+
httpGet:
|
|
582
|
+
path: /health-check
|
|
583
|
+
port: 3000
|
|
584
|
+
initialDelaySeconds: 10
|
|
585
|
+
periodSeconds: 30
|
|
586
|
+
readinessProbe:
|
|
587
|
+
httpGet:
|
|
588
|
+
path: /health-check
|
|
589
|
+
port: 3000
|
|
590
|
+
initialDelaySeconds: 5
|
|
591
|
+
periodSeconds: 10
|
|
592
|
+
resources:
|
|
593
|
+
requests:
|
|
594
|
+
memory: "256Mi"
|
|
595
|
+
cpu: "200m"
|
|
596
|
+
limits:
|
|
597
|
+
memory: "512Mi"
|
|
598
|
+
cpu: "500m"
|
|
599
|
+
---
|
|
600
|
+
apiVersion: v1
|
|
601
|
+
kind: Service
|
|
602
|
+
metadata:
|
|
603
|
+
name: ignis-service
|
|
604
|
+
spec:
|
|
605
|
+
selector:
|
|
606
|
+
app: ignis
|
|
607
|
+
ports:
|
|
608
|
+
- protocol: TCP
|
|
609
|
+
port: 80
|
|
610
|
+
targetPort: 3000
|
|
611
|
+
type: LoadBalancer
|
|
612
|
+
```
|
|
613
|
+
|
|
614
|
+
**Deploy to Kubernetes:**
|
|
615
|
+
```bash
|
|
616
|
+
# Create secrets
|
|
617
|
+
kubectl create secret generic ignis-secrets \
|
|
618
|
+
--from-literal=app-secret=$(openssl rand -base64 32) \
|
|
619
|
+
--from-literal=jwt-secret=$(openssl rand -base64 32)
|
|
620
|
+
|
|
621
|
+
# Create configmap
|
|
622
|
+
kubectl create configmap ignis-config \
|
|
623
|
+
--from-literal=db-host=postgres-service
|
|
624
|
+
|
|
625
|
+
# Apply deployment
|
|
626
|
+
kubectl apply -f k8s/
|
|
627
|
+
|
|
628
|
+
# Check status
|
|
629
|
+
kubectl get pods -l app=ignis
|
|
630
|
+
kubectl logs -l app=ignis -f
|
|
631
|
+
```
|
|
632
|
+
|
|
633
|
+
## 10. Monitoring & Observability
|
|
634
|
+
|
|
635
|
+
### Health Check Endpoints
|
|
636
|
+
|
|
637
|
+
Ignis provides built-in health checks:
|
|
638
|
+
|
|
639
|
+
```typescript
|
|
640
|
+
// In application.ts
|
|
641
|
+
import { HealthCheckComponent } from '@venizia/ignis';
|
|
642
|
+
|
|
643
|
+
this.component(HealthCheckComponent);
|
|
644
|
+
```
|
|
645
|
+
|
|
646
|
+
**Endpoints:**
|
|
647
|
+
- `GET /health-check` - Basic liveness check
|
|
648
|
+
- `GET /health-check/ready` - Readiness (includes DB connection)
|
|
649
|
+
|
|
650
|
+
### Logging in Production
|
|
651
|
+
|
|
652
|
+
Configure structured logging:
|
|
653
|
+
|
|
654
|
+
```typescript
|
|
655
|
+
import { LoggerFactory } from '@venizia/ignis-helpers';
|
|
656
|
+
|
|
657
|
+
// Set log level via environment
|
|
658
|
+
// APP_ENV_LOG_LEVEL=info (debug, info, warn, error)
|
|
659
|
+
|
|
660
|
+
const logger = LoggerFactory.getLogger(['MyService']);
|
|
661
|
+
logger.info('Service started', { port: 3000, env: 'production' });
|
|
662
|
+
```
|
|
663
|
+
|
|
664
|
+
### Metrics Collection
|
|
665
|
+
|
|
666
|
+
Add Prometheus metrics endpoint:
|
|
667
|
+
|
|
668
|
+
```typescript
|
|
669
|
+
// src/controllers/metrics.controller.ts
|
|
670
|
+
@controller({ path: '/metrics' })
|
|
671
|
+
export class MetricsController extends BaseController {
|
|
672
|
+
@get({ configs: { path: '/' } })
|
|
673
|
+
getMetrics(c: Context) {
|
|
674
|
+
return c.text(`
|
|
675
|
+
# HELP http_requests_total Total HTTP requests
|
|
676
|
+
# TYPE http_requests_total counter
|
|
677
|
+
http_requests_total{method="GET",status="200"} ${requestCount}
|
|
678
|
+
|
|
679
|
+
# HELP process_uptime_seconds Process uptime
|
|
680
|
+
# TYPE process_uptime_seconds gauge
|
|
681
|
+
process_uptime_seconds ${process.uptime()}
|
|
682
|
+
`);
|
|
683
|
+
}
|
|
684
|
+
}
|
|
685
|
+
```
|
|
686
|
+
|
|
687
|
+
## Summary
|
|
688
|
+
|
|
689
|
+
| Deployment Method | Best For | Complexity |
|
|
690
|
+
|-------------------|----------|------------|
|
|
691
|
+
| **Docker** | General production | Low |
|
|
692
|
+
| **Docker Compose** | Full stack with DB | Low |
|
|
693
|
+
| **Bun Executable** | Simple servers | Very Low |
|
|
694
|
+
| **Railway/Render** | Quick deployments | Very Low |
|
|
695
|
+
| **Fly.io** | Edge deployments | Low |
|
|
696
|
+
| **Kubernetes** | Enterprise scale | High |
|
|
697
|
+
|
|
698
|
+
Choose based on your scale and operational requirements.
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
# Best Practices
|
|
2
|
+
|
|
3
|
+
Guidelines and recommendations for building production-ready Ignis applications.
|
|
4
|
+
|
|
5
|
+
## Overview
|
|
6
|
+
|
|
7
|
+
| Guide | Description |
|
|
8
|
+
|-------|-------------|
|
|
9
|
+
| [Architectural Patterns](./architectural-patterns.md) | Layered architecture, project structure |
|
|
10
|
+
| [Architecture Decisions](./architecture-decisions.md) | When to use services, repositories, components |
|
|
11
|
+
| [Data Modeling](./data-modeling.md) | Database design, relations, migrations |
|
|
12
|
+
| [Performance Optimization](./performance-optimization.md) | Speed up your application |
|
|
13
|
+
| [Security Guidelines](./security-guidelines.md) | Protect your API and data |
|
|
14
|
+
| [Code Style Standards](./code-style-standards.md) | ESLint, Prettier, naming conventions |
|
|
15
|
+
| [Deployment Strategies](./deployment-strategies.md) | Docker, cloud platforms, CI/CD |
|
|
16
|
+
| [Common Pitfalls](./common-pitfalls.md) | Mistakes to avoid |
|
|
17
|
+
| [Troubleshooting Tips](./troubleshooting-tips.md) | Debug common issues |
|
|
18
|
+
| [API Usage Examples](./api-usage-examples.md) | Real-world code patterns |
|
|
19
|
+
| [Contribution Workflow](./contribution-workflow.md) | Contributing to Ignis |
|
|
20
|
+
|
|
21
|
+
## Quick Tips
|
|
22
|
+
|
|
23
|
+
- **Start simple** - Don't over-engineer. Add complexity only when needed.
|
|
24
|
+
- **Use the layered architecture** - Controllers → Services → Repositories
|
|
25
|
+
- **Validate early** - Use Zod schemas at API boundaries
|
|
26
|
+
- **Type everything** - Leverage TypeScript for safety
|
|
27
|
+
- **Test critical paths** - Focus on business logic and edge cases
|