bootifyjs 0.0.2 → 0.1.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/LICENSE +21 -0
- package/README.md +116 -510
- package/dist/api.d.ts +32 -0
- package/dist/api.js +149 -0
- package/dist/api.js.map +1 -0
- package/dist/config/app.config.d.ts +29 -0
- package/dist/config/app.config.js +55 -0
- package/dist/config/app.config.js.map +1 -0
- package/dist/controllers/config.controller.d.ts +16 -0
- package/dist/controllers/config.controller.js +66 -0
- package/dist/controllers/config.controller.js.map +1 -0
- package/dist/controllers/events.controller.d.ts +66 -0
- package/dist/controllers/events.controller.js +145 -0
- package/dist/controllers/events.controller.js.map +1 -0
- package/dist/controllers/health.controller.d.ts +20 -0
- package/dist/controllers/health.controller.js +92 -0
- package/dist/controllers/health.controller.js.map +1 -0
- package/dist/controllers/user.controller.d.ts +13 -0
- package/dist/controllers/user.controller.js +209 -0
- package/dist/controllers/user.controller.js.map +1 -0
- package/dist/core/application.d.ts +21 -0
- package/dist/core/application.js +90 -0
- package/dist/core/application.js.map +1 -0
- package/dist/core/config.d.ts +3 -0
- package/dist/core/config.js +78 -0
- package/dist/core/config.js.map +1 -0
- package/dist/core/container.d.ts +17 -0
- package/dist/core/container.js +92 -0
- package/dist/core/container.js.map +1 -0
- package/dist/core/decorators.d.ts +28 -0
- package/dist/core/decorators.js +204 -0
- package/dist/core/decorators.js.map +1 -0
- package/dist/core/errors.d.ts +18 -0
- package/dist/core/errors.js +74 -0
- package/dist/core/errors.js.map +1 -0
- package/dist/core/middleware.d.ts +8 -0
- package/dist/core/middleware.js +23 -0
- package/dist/core/middleware.js.map +1 -0
- package/dist/core/openapi.d.ts +80 -0
- package/dist/core/openapi.js +189 -0
- package/dist/core/openapi.js.map +1 -0
- package/dist/core/router.d.ts +32 -0
- package/dist/core/router.js +266 -0
- package/dist/core/router.js.map +1 -0
- package/dist/core/utils.d.ts +7 -0
- package/dist/core/utils.js +75 -0
- package/dist/core/utils.js.map +1 -0
- package/dist/core/validation.d.ts +15 -0
- package/dist/core/validation.js +161 -0
- package/dist/core/validation.js.map +1 -0
- package/dist/events/core/event-bus.d.ts +26 -0
- package/dist/events/core/event-bus.js +253 -0
- package/dist/events/core/event-bus.js.map +1 -0
- package/dist/events/core/event-registry.d.ts +31 -0
- package/dist/events/core/event-registry.js +170 -0
- package/dist/events/core/event-registry.js.map +1 -0
- package/dist/events/decorators/event.decorators.d.ts +11 -0
- package/dist/events/decorators/event.decorators.js +123 -0
- package/dist/events/decorators/event.decorators.js.map +1 -0
- package/dist/events/examples/system.events.d.ts +15 -0
- package/dist/events/examples/system.events.js +28 -0
- package/dist/events/examples/system.events.js.map +1 -0
- package/dist/events/examples/user.events.d.ts +68 -0
- package/dist/events/examples/user.events.js +73 -0
- package/dist/events/examples/user.events.js.map +1 -0
- package/dist/events/examples/user.handlers.d.ts +20 -0
- package/dist/events/examples/user.handlers.js +157 -0
- package/dist/events/examples/user.handlers.js.map +1 -0
- package/dist/events/index.d.ts +13 -0
- package/dist/events/index.js +71 -0
- package/dist/events/index.js.map +1 -0
- package/dist/events/middleware/logging.middleware.d.ts +7 -0
- package/dist/events/middleware/logging.middleware.js +44 -0
- package/dist/events/middleware/logging.middleware.js.map +1 -0
- package/dist/events/middleware/metrics.middleware.d.ts +11 -0
- package/dist/events/middleware/metrics.middleware.js +87 -0
- package/dist/events/middleware/metrics.middleware.js.map +1 -0
- package/dist/events/middleware/validation.middleware.d.ts +8 -0
- package/dist/events/middleware/validation.middleware.js +63 -0
- package/dist/events/middleware/validation.middleware.js.map +1 -0
- package/dist/events/store/memory-event-store.d.ts +21 -0
- package/dist/events/store/memory-event-store.js +81 -0
- package/dist/events/store/memory-event-store.js.map +1 -0
- package/dist/events/types/event.types.d.ts +57 -0
- package/dist/{decorators/cache/ICacheClient.js → events/types/event.types.js} +1 -1
- package/dist/events/types/event.types.js.map +1 -0
- package/dist/examples/basic-api.d.ts +1 -0
- package/dist/examples/basic-api.js +120 -0
- package/dist/examples/basic-api.js.map +1 -0
- package/dist/index.d.ts +17 -11
- package/dist/index.js +95 -31
- package/dist/index.js.map +1 -1
- package/dist/logging/config/logging.config.d.ts +5 -0
- package/dist/logging/config/logging.config.js +101 -0
- package/dist/logging/config/logging.config.js.map +1 -0
- package/dist/logging/core/log-context.service.d.ts +11 -0
- package/dist/logging/core/log-context.service.js +40 -0
- package/dist/logging/core/log-context.service.js.map +1 -0
- package/dist/logging/core/logger.service.d.ts +29 -0
- package/dist/logging/core/logger.service.js +178 -0
- package/dist/logging/core/logger.service.js.map +1 -0
- package/dist/logging/core/startup-logger.service.d.ts +17 -0
- package/dist/logging/core/startup-logger.service.js +156 -0
- package/dist/logging/core/startup-logger.service.js.map +1 -0
- package/dist/logging/decorators/log.decorator.d.ts +11 -0
- package/dist/logging/decorators/log.decorator.js +80 -0
- package/dist/logging/decorators/log.decorator.js.map +1 -0
- package/dist/logging/index.d.ts +15 -0
- package/dist/logging/index.js +46 -0
- package/dist/logging/index.js.map +1 -0
- package/dist/logging/middleware/context.middleware.d.ts +2 -0
- package/dist/logging/middleware/context.middleware.js +29 -0
- package/dist/logging/middleware/context.middleware.js.map +1 -0
- package/dist/logging/middleware/request-logging.middleware.d.ts +3 -0
- package/dist/logging/middleware/request-logging.middleware.js +78 -0
- package/dist/logging/middleware/request-logging.middleware.js.map +1 -0
- package/dist/logging/types/logging.types.d.ts +79 -0
- package/dist/{decorators/transaction/IDatabaseClient.js → logging/types/logging.types.js} +1 -1
- package/dist/logging/types/logging.types.js.map +1 -0
- package/dist/middlewares/auth.middleware.d.ts +2 -0
- package/dist/middlewares/auth.middleware.js +20 -0
- package/dist/middlewares/auth.middleware.js.map +1 -0
- package/dist/middlewares/cors.middleware.d.ts +2 -0
- package/dist/middlewares/cors.middleware.js +16 -0
- package/dist/middlewares/cors.middleware.js.map +1 -0
- package/dist/middlewares/swagger.middleware.d.ts +6 -0
- package/dist/middlewares/swagger.middleware.js +84 -0
- package/dist/middlewares/swagger.middleware.js.map +1 -0
- package/dist/repositories/user.repository.d.ts +16 -0
- package/dist/repositories/user.repository.js +110 -0
- package/dist/repositories/user.repository.js.map +1 -0
- package/dist/schemas/user.schemas.d.ts +214 -0
- package/dist/schemas/user.schemas.js +71 -0
- package/dist/schemas/user.schemas.js.map +1 -0
- package/dist/services/config-demo.service.d.ts +10 -0
- package/dist/services/config-demo.service.js +88 -0
- package/dist/services/config-demo.service.js.map +1 -0
- package/dist/services/user.service.d.ts +21 -0
- package/dist/services/user.service.js +201 -0
- package/dist/services/user.service.js.map +1 -0
- package/package.json +49 -14
- package/dist/application/Application.d.ts +0 -43
- package/dist/application/Application.d.ts.map +0 -1
- package/dist/application/Application.js +0 -283
- package/dist/application/Application.js.map +0 -1
- package/dist/container/container.d.ts +0 -9
- package/dist/container/container.d.ts.map +0 -1
- package/dist/container/container.js +0 -23
- package/dist/container/container.js.map +0 -1
- package/dist/decorators/cache/ICacheClient.d.ts +0 -6
- package/dist/decorators/cache/ICacheClient.d.ts.map +0 -1
- package/dist/decorators/cache/ICacheClient.js.map +0 -1
- package/dist/decorators/cache/cache.decorator.d.ts +0 -2
- package/dist/decorators/cache/cache.decorator.d.ts.map +0 -1
- package/dist/decorators/cache/cache.decorator.js +0 -38
- package/dist/decorators/cache/cache.decorator.js.map +0 -1
- package/dist/decorators/controller.decorator.d.ts +0 -9
- package/dist/decorators/controller.decorator.d.ts.map +0 -1
- package/dist/decorators/controller.decorator.js +0 -99
- package/dist/decorators/controller.decorator.js.map +0 -1
- package/dist/decorators/http.decorator.d.ts +0 -7
- package/dist/decorators/http.decorator.d.ts.map +0 -1
- package/dist/decorators/http.decorator.js +0 -26
- package/dist/decorators/http.decorator.js.map +0 -1
- package/dist/decorators/timing.decorator.d.ts +0 -2
- package/dist/decorators/timing.decorator.d.ts.map +0 -1
- package/dist/decorators/timing.decorator.js +0 -26
- package/dist/decorators/timing.decorator.js.map +0 -1
- package/dist/decorators/transaction/IDatabaseClient.d.ts +0 -9
- package/dist/decorators/transaction/IDatabaseClient.d.ts.map +0 -1
- package/dist/decorators/transaction/IDatabaseClient.js.map +0 -1
- package/dist/decorators/transaction/transactional.decorator.d.ts +0 -2
- package/dist/decorators/transaction/transactional.decorator.d.ts.map +0 -1
- package/dist/decorators/transaction/transactional.decorator.js +0 -27
- package/dist/decorators/transaction/transactional.decorator.js.map +0 -1
- package/dist/index.d.ts.map +0 -1
- package/dist/logger/Logger.d.ts +0 -37
- package/dist/logger/Logger.d.ts.map +0 -1
- package/dist/logger/Logger.js +0 -142
- package/dist/logger/Logger.js.map +0 -1
- package/dist/middleware/http.d.ts +0 -2
- package/dist/middleware/http.d.ts.map +0 -1
- package/dist/middleware/http.js +0 -80
- package/dist/middleware/http.js.map +0 -1
- package/dist/middleware/requestcontext.d.ts +0 -12
- package/dist/middleware/requestcontext.d.ts.map +0 -1
- package/dist/middleware/requestcontext.js +0 -6
- package/dist/middleware/requestcontext.js.map +0 -1
- package/src/application/Application.ts +0 -355
- package/src/container/container.ts +0 -28
- package/src/decorators/cache/ICacheClient.ts +0 -5
- package/src/decorators/cache/cache.decorator.ts +0 -36
- package/src/decorators/controller.decorator.ts +0 -119
- package/src/decorators/http.decorator.ts +0 -25
- package/src/decorators/timing.decorator.ts +0 -23
- package/src/decorators/transaction/IDatabaseClient.ts +0 -9
- package/src/decorators/transaction/transactional.decorator.ts +0 -24
- package/src/index.ts +0 -10
- package/src/logger/Logger.ts +0 -179
- package/src/middleware/http.ts +0 -81
- package/src/middleware/requestcontext.ts +0 -12
package/README.md
CHANGED
@@ -1,567 +1,173 @@
|
|
1
|
-
#
|
2
|
-
|
3
|
-
A production-ready, Spring Boot-inspired TypeScript framework built on top of Fastify and express, designed for building scalable enterprise applications with modern development practices.
|
4
|
-
|
5
|
-
## 🎯 Why This Framework?
|
6
|
-
|
7
|
-
### The Problem
|
8
|
-
Building enterprise-grade Node.js applications often involves:
|
9
|
-
- ⚡ Repetitive boilerplate code for common patterns
|
10
|
-
- 🔧 Manual setup of logging, caching, validation, and error handling
|
11
|
-
- 📦 Inconsistent project structure across teams
|
12
|
-
- 🏗️ Lack of standardized dependency injection
|
13
|
-
- 🔄 Manual configuration of database connections and migrations
|
14
|
-
- 📊 Missing observability and monitoring out-of-the-box
|
15
|
-
|
16
|
-
### The Solution
|
17
|
-
Our framework provides:
|
18
|
-
- 🎨 **Spring Boot-style decorators** (`@Controller`, `@Service`, `@Repository`)
|
19
|
-
- 🏗️ **Dependency Injection** with Inversify
|
20
|
-
- 🚀 **High-performance** Fastify web server
|
21
|
-
- 📊 **Built-in observability** (logging, metrics, tracing)
|
22
|
-
- 💾 **Integrated caching** with Redis
|
23
|
-
- 🗄️ **Database abstraction** with Sequelize ORM
|
24
|
-
- 🔧 **Zero-config setup** for common enterprise patterns
|
25
|
-
- 📦 **Monorepo structure** for scalable team development
|
26
|
-
|
27
|
-
## 🏗️ Architecture Overview
|
1
|
+
# BootifyJS
|
28
2
|
|
29
|
-
|
30
|
-
┌─────────────────────────────────────────────────────────────┐
|
31
|
-
│ Application Layer │
|
32
|
-
│ ┌─────────────────┐ ┌─────────────────┐ ┌──────────────┐ │
|
33
|
-
│ │ CMS APIs │ │ Consumer APIs │ │ Admin APIs │ │
|
34
|
-
│ │ @Controller │ │ @Controller │ │ @Controller │ │
|
35
|
-
│ └─────────────────┘ └─────────────────┘ └──────────────┘ │
|
36
|
-
└─────────────────────────────────────────────────────────────┘
|
37
|
-
┌─────────────────────────────────────────────────────────────┐
|
38
|
-
│ Service Layer │
|
39
|
-
│ ┌─────────────────┐ ┌─────────────────┐ ┌──────────────┐ │
|
40
|
-
│ │ UserService │ │ OrderService │ │ EmailService │ │
|
41
|
-
│ │ @Service │ │ @Service │ │ @Service │ │
|
42
|
-
│ └─────────────────┘ └─────────────────┘ └──────────────┘ │
|
43
|
-
└─────────────────────────────────────────────────────────────┘
|
44
|
-
┌─────────────────────────────────────────────────────────────┐
|
45
|
-
│ Repository Layer │
|
46
|
-
│ ┌─────────────────┐ ┌─────────────────┐ ┌──────────────┐ │
|
47
|
-
│ │ UserRepository │ │ OrderRepository │ │EmailTemplate │ │
|
48
|
-
│ │ @Repository │ │ @Repository │ │ @Repository │ │
|
49
|
-
│ └─────────────────┘ └─────────────────┘ └──────────────┘ │
|
50
|
-
└─────────────────────────────────────────────────────────────┘
|
51
|
-
┌─────────────────────────────────────────────────────────────┐
|
52
|
-
│ Core Framework │
|
53
|
-
│ Fastify + Decorators + DI + Caching + Logging │
|
54
|
-
└─────────────────────────────────────────────────────────────┘
|
55
|
-
```
|
56
|
-
|
57
|
-
## 📦 Package Structure
|
58
|
-
|
59
|
-
### `core` - Framework Foundation
|
60
|
-
- 🎯 **Application bootstrapping** with configurable features
|
61
|
-
- 🏗️ **Dependency injection** container with decorators
|
62
|
-
- 🌐 **HTTP decorators** (`@Get`, `@Post`, `@Put`, `@Delete`)
|
63
|
-
- ⚡ **Performance decorators** (`@Timed`, `@Cache`)
|
64
|
-
- 📊 **Structured logging** (Application, Audit, Event logs)
|
65
|
-
- 🔄 **Transaction management** with `@Transactional`
|
66
|
-
|
67
|
-
### `commons` - Shared Components
|
68
|
-
- 🗄️ **Database clients** (Sequelize, Redis)
|
69
|
-
- 📋 **Base repository** with caching and pagination
|
70
|
-
- 🔧 **Database migrations** and seeders
|
71
|
-
- 🏷️ **Shared models** and interfaces
|
72
|
-
|
73
|
-
### `@monorepo/cms-apis` - Example Application
|
74
|
-
- 🎮 **Controllers** using framework decorators
|
75
|
-
- 💼 **Business logic** with service layer
|
76
|
-
- 📊 **Complete CRUD** operations with caching
|
77
|
-
|
78
|
-
## 🚀 Quick Start
|
79
|
-
|
80
|
-
### Prerequisites
|
81
|
-
- Node.js 18+
|
82
|
-
- PostgreSQL 12+
|
83
|
-
- Redis 6+ (optional, for caching)
|
84
|
-
|
85
|
-
### Installation
|
86
|
-
|
87
|
-
```bash
|
88
|
-
# Clone the repository
|
89
|
-
git clone <repository-url>
|
90
|
-
cd typescript-fastify-framework
|
91
|
-
|
92
|
-
# Install dependencies for all packages
|
93
|
-
npm install
|
94
|
-
|
95
|
-
# Build all packages
|
96
|
-
npm run build
|
97
|
-
```
|
3
|
+
A Spring Boot inspired Node.js framework with TypeScript, Dependency Injection, and Validation.
|
98
4
|
|
99
|
-
|
5
|
+
## Installation
|
100
6
|
|
101
7
|
```bash
|
102
|
-
|
103
|
-
cp packages/cms-apis/.env.example packages/cms-apis/.env
|
104
|
-
|
105
|
-
# Edit with your configuration
|
106
|
-
nano packages/cms-apis/.env
|
107
|
-
```
|
108
|
-
|
109
|
-
### Database Setup
|
110
|
-
|
111
|
-
```bash
|
112
|
-
# Navigate to commons package
|
113
|
-
cd packages/commons
|
114
|
-
|
115
|
-
# Create database
|
116
|
-
npm run db:create
|
117
|
-
|
118
|
-
# Run migrations
|
119
|
-
npm run db:migrate
|
120
|
-
|
121
|
-
# Seed with sample data (optional)
|
122
|
-
npm run db:seed
|
8
|
+
npm install bootifyjs
|
123
9
|
```
|
124
10
|
|
125
|
-
|
126
|
-
|
127
|
-
```bash
|
128
|
-
# From root directory
|
129
|
-
npm run dev
|
130
|
-
```
|
131
|
-
|
132
|
-
🎉 **Your API is now running at `http://localhost:3000`**
|
133
|
-
|
134
|
-
## 📚 Core Concepts
|
135
|
-
|
136
|
-
### 1. Controllers - HTTP Entry Points
|
11
|
+
## Quick Start
|
137
12
|
|
138
13
|
```typescript
|
139
|
-
import { Controller, Get,
|
140
|
-
import { inject } from 'inversify';
|
141
|
-
|
142
|
-
@Controller('/api/users')
|
143
|
-
export class UserController {
|
144
|
-
constructor(
|
145
|
-
@inject(UserService) private userService: UserService
|
146
|
-
) {}
|
147
|
-
|
148
|
-
@Get('/')
|
149
|
-
async getAllUsers() {
|
150
|
-
return this.userService.findAllUsers();
|
151
|
-
}
|
14
|
+
import { createBootifyApp, Controller, Get, Service } from 'bootifyjs';
|
152
15
|
|
153
|
-
|
154
|
-
|
155
|
-
|
156
|
-
|
157
|
-
required: ['email', 'firstName', 'lastName'],
|
158
|
-
properties: {
|
159
|
-
email: { type: 'string', format: 'email' },
|
160
|
-
firstName: { type: 'string', minLength: 1 },
|
161
|
-
lastName: { type: 'string', minLength: 1 }
|
162
|
-
}
|
163
|
-
}
|
164
|
-
}
|
165
|
-
})
|
166
|
-
async createUser(request: FastifyRequest<CreateUserRequest>) {
|
167
|
-
return this.userService.createUser(request.body);
|
16
|
+
@Service()
|
17
|
+
class GreetingService {
|
18
|
+
getGreeting(name: string) {
|
19
|
+
return `Hello, ${name}!`;
|
168
20
|
}
|
169
21
|
}
|
170
|
-
```
|
171
22
|
|
172
|
-
|
173
|
-
|
174
|
-
|
175
|
-
|
176
|
-
|
177
|
-
|
178
|
-
|
179
|
-
export class UserService {
|
180
|
-
constructor(
|
181
|
-
@inject(UserRepository) private userRepository: UserRepository
|
182
|
-
) {}
|
183
|
-
|
184
|
-
@Timed() // Automatically logs execution time
|
185
|
-
async createUser(userData: CreateUserData): Promise<User> {
|
186
|
-
Logger.info(`Creating user: ${userData.email}`);
|
187
|
-
|
188
|
-
// Business logic here
|
189
|
-
const user = await this.userRepository.create(userData);
|
190
|
-
|
191
|
-
// Audit logging
|
192
|
-
AuditLogger.info({
|
193
|
-
userId: 'system',
|
194
|
-
action: 'CREATE_USER',
|
195
|
-
resources: ['users'],
|
196
|
-
data: { userId: user.id, email: user.email }
|
197
|
-
});
|
198
|
-
|
199
|
-
return user;
|
23
|
+
@Controller('/api')
|
24
|
+
class GreetingController {
|
25
|
+
constructor(private greetingService: GreetingService) {}
|
26
|
+
|
27
|
+
@Get('/hello')
|
28
|
+
sayHello() {
|
29
|
+
return { message: this.greetingService.getGreeting('World') };
|
200
30
|
}
|
201
31
|
}
|
202
|
-
```
|
203
|
-
|
204
|
-
### 3. Repositories - Data Access Layer
|
205
|
-
|
206
|
-
```typescript
|
207
|
-
import { Repository, AppRepository } from '@monorepo/core';
|
208
|
-
|
209
|
-
@Repository('singleton')
|
210
|
-
export class UserRepository extends AppRepository<User> {
|
211
|
-
constructor() {
|
212
|
-
super(User, {
|
213
|
-
cacheTTL: 3600, // 1 hour cache
|
214
|
-
defaultFields: ['id', 'email', 'firstName', 'lastName', 'isActive']
|
215
|
-
});
|
216
|
-
}
|
217
|
-
|
218
|
-
// Custom methods with automatic caching
|
219
|
-
async findByEmail(email: string): Promise<User | null> {
|
220
|
-
return this.findOne({ where: { email } });
|
221
|
-
}
|
222
32
|
|
223
|
-
|
224
|
-
|
225
|
-
|
33
|
+
async function main() {
|
34
|
+
const { start } = await createBootifyApp({
|
35
|
+
port: 3000,
|
36
|
+
controllers: [GreetingController],
|
37
|
+
enableSwagger: true
|
38
|
+
});
|
39
|
+
|
40
|
+
await start();
|
41
|
+
console.log('Server running at http://localhost:3000');
|
226
42
|
}
|
227
|
-
```
|
228
|
-
|
229
|
-
### 4. Application Bootstrap
|
230
43
|
|
231
|
-
|
232
|
-
import { Application, Logger } from '@monorepo/core';
|
233
|
-
|
234
|
-
const app = new Application({
|
235
|
-
port: 3000,
|
236
|
-
enableCors: true,
|
237
|
-
enableSwagger: true,
|
238
|
-
enableMetrics: true,
|
239
|
-
corsOptions: {
|
240
|
-
origin: ['http://localhost:3000', 'https://yourdomain.com'],
|
241
|
-
credentials: true
|
242
|
-
}
|
243
|
-
});
|
244
|
-
|
245
|
-
// Register controllers
|
246
|
-
app.registerControllers([
|
247
|
-
UserController,
|
248
|
-
OrderController,
|
249
|
-
HealthController
|
250
|
-
]);
|
251
|
-
|
252
|
-
await app.start();
|
44
|
+
main().catch(console.error);
|
253
45
|
```
|
254
46
|
|
255
|
-
##
|
256
|
-
|
257
|
-
### Application Configuration
|
258
|
-
|
259
|
-
```typescript
|
260
|
-
interface FastifyServerConfig {
|
261
|
-
port?: number; // Server port (default: 3000)
|
262
|
-
host?: string; // Server host (default: '0.0.0.0')
|
263
|
-
enableCors?: boolean; // Enable CORS (default: true)
|
264
|
-
enableSwagger?: boolean; // Enable API docs (default: false)
|
265
|
-
enableLogging?: boolean; // Enable request logging (default: true)
|
266
|
-
enableErrorHandling?: boolean; // Global error handler (default: true)
|
267
|
-
enableMetrics?: boolean; // Prometheus metrics (default: false)
|
268
|
-
enableCookie?: boolean; // Cookie support (default: false)
|
269
|
-
enableAuth?: boolean; // Authentication middleware (default: false)
|
270
|
-
corsOptions?: CorsOptions; // CORS configuration
|
271
|
-
swaggerOptions?: SwaggerOptions; // Swagger configuration
|
272
|
-
}
|
273
|
-
```
|
274
|
-
|
275
|
-
### Environment Variables
|
276
|
-
|
277
|
-
```bash
|
278
|
-
# Database Configuration
|
279
|
-
DB_NAME=your_database
|
280
|
-
DB_USER=postgres
|
281
|
-
DB_PASS=password
|
282
|
-
DB_HOST=localhost
|
283
|
-
DB_PORT=5432
|
284
|
-
DB_DIALECT=postgres
|
285
|
-
|
286
|
-
# Redis Configuration (optional)
|
287
|
-
REDIS_HOST=localhost
|
288
|
-
REDIS_PORT=6379
|
289
|
-
REDIS_PASSWORD=
|
290
|
-
|
291
|
-
# Application Configuration
|
292
|
-
APP_PORT=3000
|
293
|
-
NODE_ENV=development
|
294
|
-
LOG_LEVEL=info
|
295
|
-
```
|
47
|
+
## Simple Configuration Management
|
296
48
|
|
297
|
-
|
49
|
+
The framework provides a very simple configuration management system that automatically maps environment variables to nested configuration properties.
|
298
50
|
|
299
|
-
###
|
300
|
-
Visit `http://localhost:3000/docs` when `enableSwagger: true`
|
51
|
+
### How It Works
|
301
52
|
|
302
|
-
|
303
|
-
|
304
|
-
|
53
|
+
1. **Single Configuration Class**: Define one `AppConfig` class with your configuration structure
|
54
|
+
2. **Automatic Mapping**: Environment variables with `BOOTIFY_` prefix are automatically mapped to nested properties
|
55
|
+
3. **Type Conversion**: Values are automatically converted to numbers and booleans when possible
|
305
56
|
|
306
|
-
###
|
307
|
-
- `GET /metrics` - Prometheus metrics (when enabled)
|
308
|
-
- Automatic request timing and counting
|
309
|
-
- Error rate monitoring
|
57
|
+
### Usage
|
310
58
|
|
311
|
-
|
59
|
+
**1. Define Your Configuration Structure:**
|
312
60
|
```typescript
|
313
|
-
|
314
|
-
|
315
|
-
|
316
|
-
|
317
|
-
|
318
|
-
|
319
|
-
|
320
|
-
|
321
|
-
|
322
|
-
|
323
|
-
|
324
|
-
|
325
|
-
|
326
|
-
|
327
|
-
|
328
|
-
|
329
|
-
|
330
|
-
|
331
|
-
|
332
|
-
|
333
|
-
|
334
|
-
|
335
|
-
|
336
|
-
|
337
|
-
GET /api/users
|
338
|
-
|
339
|
-
# Get user by ID
|
340
|
-
GET /api/users/:id
|
341
|
-
|
342
|
-
# Get user by email
|
343
|
-
GET /api/users/email/:email
|
344
|
-
|
345
|
-
# Create user
|
346
|
-
POST /api/users
|
347
|
-
{
|
348
|
-
"email": "john@example.com",
|
349
|
-
"firstName": "John",
|
350
|
-
"lastName": "Doe"
|
351
|
-
}
|
352
|
-
|
353
|
-
# Update user
|
354
|
-
PUT /api/users/:id
|
355
|
-
{
|
356
|
-
"firstName": "Jane"
|
61
|
+
import { Config } from '../core/config';
|
62
|
+
|
63
|
+
@Config('BOOTIFY')
|
64
|
+
export class AppConfig {
|
65
|
+
SERVICE_NAME: string = 'bootifyjs-app';
|
66
|
+
|
67
|
+
server: {
|
68
|
+
port: number;
|
69
|
+
host: string;
|
70
|
+
name?: string;
|
71
|
+
} = {
|
72
|
+
port: 3000,
|
73
|
+
host: 'localhost'
|
74
|
+
};
|
75
|
+
|
76
|
+
database: {
|
77
|
+
host: string;
|
78
|
+
port: number;
|
79
|
+
name: string;
|
80
|
+
} = {
|
81
|
+
host: 'localhost',
|
82
|
+
port: 5432,
|
83
|
+
name: 'myapp'
|
84
|
+
};
|
357
85
|
}
|
358
|
-
|
359
|
-
# Delete user (soft delete)
|
360
|
-
DELETE /api/users/:id
|
361
|
-
|
362
|
-
# Get user statistics
|
363
|
-
GET /api/users/stats
|
364
|
-
|
365
|
-
# Paginated users
|
366
|
-
GET /api/users/paginate?page=1&limit=10
|
367
86
|
```
|
368
87
|
|
369
|
-
|
88
|
+
**2. Set Environment Variables:**
|
370
89
|
```bash
|
371
|
-
#
|
372
|
-
|
90
|
+
# Maps to appConfig.SERVICE_NAME
|
91
|
+
BOOTIFY_SERVICE_NAME=my-awesome-app
|
373
92
|
|
374
|
-
#
|
375
|
-
|
93
|
+
# Maps to appConfig.server.port
|
94
|
+
BOOTIFY_SERVER_PORT=8080
|
376
95
|
|
377
|
-
#
|
378
|
-
|
379
|
-
```
|
96
|
+
# Maps to appConfig.server.host
|
97
|
+
BOOTIFY_SERVER_HOST=0.0.0.0
|
380
98
|
|
381
|
-
|
99
|
+
# Maps to appConfig.server.name
|
100
|
+
BOOTIFY_SERVER_NAME=my-server
|
382
101
|
|
383
|
-
|
102
|
+
# Maps to appConfig.database.host
|
103
|
+
BOOTIFY_DATABASE_HOST=postgres-server
|
384
104
|
|
385
|
-
|
386
|
-
|
387
|
-
// packages/commons/src/models/Product.ts
|
388
|
-
export class Product extends Model {
|
389
|
-
public id!: number;
|
390
|
-
public name!: string;
|
391
|
-
public price!: number;
|
392
|
-
}
|
105
|
+
# Maps to appConfig.database.port
|
106
|
+
BOOTIFY_DATABASE_PORT=5432
|
393
107
|
```
|
394
108
|
|
395
|
-
|
109
|
+
**3. Access Configuration:**
|
396
110
|
```typescript
|
397
|
-
|
398
|
-
|
399
|
-
export class ProductRepository extends AppRepository<Product> {
|
400
|
-
constructor() {
|
401
|
-
super(Product, { cacheTTL: 1800 });
|
402
|
-
}
|
403
|
-
}
|
404
|
-
```
|
111
|
+
import { getConfigInstance } from './core/config';
|
112
|
+
import { AppConfig } from './config/app.config';
|
405
113
|
|
406
|
-
|
407
|
-
```typescript
|
408
|
-
// packages/commons/src/services/ProductService.ts
|
409
|
-
@Service('singleton')
|
410
|
-
export class ProductService {
|
411
|
-
constructor(
|
412
|
-
@inject(ProductRepository) private productRepo: ProductRepository
|
413
|
-
) {}
|
414
|
-
|
415
|
-
@Timed()
|
416
|
-
async createProduct(data: CreateProductData): Promise<Product> {
|
417
|
-
return this.productRepo.create(data);
|
418
|
-
}
|
419
|
-
}
|
420
|
-
```
|
114
|
+
const appConfig = getConfigInstance(AppConfig);
|
421
115
|
|
422
|
-
|
423
|
-
|
424
|
-
//
|
425
|
-
|
426
|
-
export class ProductController {
|
427
|
-
constructor(
|
428
|
-
@inject(ProductService) private productService: ProductService
|
429
|
-
) {}
|
430
|
-
|
431
|
-
@Post('/')
|
432
|
-
async createProduct(request: FastifyRequest) {
|
433
|
-
return this.productService.createProduct(request.body);
|
434
|
-
}
|
435
|
-
}
|
116
|
+
console.log(appConfig.SERVICE_NAME); // 'my-awesome-app'
|
117
|
+
console.log(appConfig.server.port); // 8080
|
118
|
+
console.log(appConfig.server.host); // '0.0.0.0'
|
119
|
+
console.log(appConfig.database.host); // 'postgres-server'
|
436
120
|
```
|
437
121
|
|
438
|
-
|
122
|
+
**4. Inject into Services:**
|
439
123
|
```typescript
|
440
|
-
|
441
|
-
|
442
|
-
|
443
|
-
|
444
|
-
|
445
|
-
|
446
|
-
|
447
|
-
|
448
|
-
|
449
|
-
|
450
|
-
```bash
|
451
|
-
# Run all tests
|
452
|
-
npm run test
|
453
|
-
|
454
|
-
# Run tests for specific package
|
455
|
-
npm run test --workspace=packages/core
|
456
|
-
|
457
|
-
# Run tests in watch mode
|
458
|
-
npm run test:watch
|
459
|
-
```
|
460
|
-
|
461
|
-
## 📦 Building & Deployment
|
462
|
-
|
463
|
-
### Development
|
464
|
-
```bash
|
465
|
-
npm run dev
|
466
|
-
```
|
467
|
-
|
468
|
-
### Production Build
|
469
|
-
```bash
|
470
|
-
npm run build
|
471
|
-
npm run start
|
472
|
-
```
|
473
|
-
|
474
|
-
### Docker Deployment
|
475
|
-
```dockerfile
|
476
|
-
FROM node:18-alpine
|
477
|
-
WORKDIR /app
|
478
|
-
COPY package*.json ./
|
479
|
-
RUN npm ci --only=production
|
480
|
-
COPY dist/ ./dist/
|
481
|
-
EXPOSE 3000
|
482
|
-
CMD ["npm", "start"]
|
483
|
-
```
|
484
|
-
|
485
|
-
## 🔧 Advanced Usage
|
486
|
-
|
487
|
-
### Custom Decorators
|
488
|
-
```typescript
|
489
|
-
// Create custom validation decorator
|
490
|
-
export function ValidateUser(): MethodDecorator {
|
491
|
-
return (target, propertyKey, descriptor) => {
|
492
|
-
// Custom validation logic
|
493
|
-
};
|
494
|
-
}
|
495
|
-
|
496
|
-
// Usage
|
497
|
-
@Controller('/api/users')
|
498
|
-
export class UserController {
|
499
|
-
@Post('/')
|
500
|
-
@ValidateUser()
|
501
|
-
async createUser(request: FastifyRequest) {
|
502
|
-
// Method implementation
|
124
|
+
import { InjectConfig } from './core/decorators';
|
125
|
+
|
126
|
+
@Service()
|
127
|
+
export class MyService {
|
128
|
+
constructor(@InjectConfig(AppConfig) private config: AppConfig) {}
|
129
|
+
|
130
|
+
doSomething() {
|
131
|
+
console.log(`Service: ${this.config.SERVICE_NAME}`);
|
132
|
+
console.log(`Running on port: ${this.config.server.port}`);
|
503
133
|
}
|
504
134
|
}
|
505
135
|
```
|
506
136
|
|
507
|
-
###
|
508
|
-
```typescript
|
509
|
-
const app = new Application({
|
510
|
-
// ... other config
|
511
|
-
});
|
512
|
-
|
513
|
-
// Add custom middleware
|
514
|
-
app.getServer().addHook('preHandler', async (request, reply) => {
|
515
|
-
// Custom logic before request handling
|
516
|
-
});
|
517
|
-
```
|
137
|
+
### Environment Variable Mapping Rules
|
518
138
|
|
519
|
-
|
520
|
-
```typescript
|
521
|
-
@Service('singleton')
|
522
|
-
export class OrderService {
|
523
|
-
@Transactional()
|
524
|
-
async createOrderWithItems(orderData: CreateOrderData, transaction?: Transaction) {
|
525
|
-
// All database operations will use the same transaction
|
526
|
-
const order = await this.orderRepo.create(orderData, { transaction });
|
527
|
-
const items = await this.orderItemRepo.bulkCreate(orderData.items, { transaction });
|
528
|
-
|
529
|
-
// Transaction automatically committed on success
|
530
|
-
// or rolled back on error
|
531
|
-
return { order, items };
|
532
|
-
}
|
533
|
-
}
|
534
|
-
```
|
139
|
+
The system automatically converts environment variable names to nested property paths:
|
535
140
|
|
536
|
-
|
141
|
+
- `BOOTIFY_SERVICE_NAME` → `appConfig.SERVICE_NAME`
|
142
|
+
- `BOOTIFY_SERVER_PORT` → `appConfig.server.port`
|
143
|
+
- `BOOTIFY_SERVER_HOST` → `appConfig.server.host`
|
144
|
+
- `BOOTIFY_DATABASE_HOST` → `appConfig.database.host`
|
145
|
+
- `BOOTIFY_DATABASE_PORT` → `appConfig.database.port`
|
537
146
|
|
538
|
-
|
539
|
-
2. Create your feature branch (`git checkout -b feature/amazing-feature`)
|
540
|
-
3. Commit your changes (`git commit -m 'Add amazing feature'`)
|
541
|
-
4. Push to the branch (`git push origin feature/amazing-feature`)
|
542
|
-
5. Open a Pull Request
|
147
|
+
### Automatic Type Conversion
|
543
148
|
|
544
|
-
|
149
|
+
- **Numbers**: `"8080"` → `8080`
|
150
|
+
- **Booleans**: `"true"` → `true`, `"false"` → `false`
|
151
|
+
- **Strings**: Everything else remains as string
|
545
152
|
|
546
|
-
|
153
|
+
### Getting Started
|
547
154
|
|
548
|
-
|
155
|
+
1. Copy `example.env` to `.env` and modify values
|
156
|
+
2. Set your environment variables following the `BOOTIFY_*` pattern
|
157
|
+
3. Access your configuration using `getConfigInstance(AppConfig)`
|
549
158
|
|
550
|
-
-
|
551
|
-
- 💬 **Discord**: [Community chat]
|
552
|
-
- 🐛 **Issues**: [GitHub Issues]
|
553
|
-
- 📧 **Email**: support@yourframework.com
|
159
|
+
That's it! No complex setup, no manual property mapping - just define your structure and set your environment variables.
|
554
160
|
|
555
|
-
##
|
161
|
+
## Features
|
556
162
|
|
557
|
-
-
|
558
|
-
-
|
559
|
-
-
|
560
|
-
-
|
561
|
-
-
|
562
|
-
-
|
563
|
-
-
|
163
|
+
- **Dependency Injection**: Automatic constructor injection with `@Injectable`, `@Service`, and `@Repository` decorators
|
164
|
+
- **REST API**: Easy controller definition with `@Controller`, `@Get`, `@Post`, etc.
|
165
|
+
- **Validation**: Request validation with Zod schemas
|
166
|
+
- **Configuration**: Environment-based configuration with automatic mapping
|
167
|
+
- **OpenAPI**: Automatic OpenAPI documentation generation
|
168
|
+
- **Logging**: Comprehensive logging system with context tracking
|
169
|
+
- **Event System**: Type-safe event system with middleware support
|
564
170
|
|
565
|
-
|
171
|
+
## Documentation
|
566
172
|
|
567
|
-
|
173
|
+
For more detailed documentation, please visit our [GitHub repository](https://github.com/bootifyjs/bootifyjs).
|