@onlineapps/service-wrapper 2.0.7 → 2.0.9

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,261 @@
1
+ # Service Configuration Guide
2
+
3
+ ## Configuration Directory Structure
4
+
5
+ Every service must have a `conn-config/` directory with these configuration files:
6
+
7
+ ```
8
+ /service-root
9
+ /conn-config
10
+ config.json # Main service configuration
11
+ operations.json # Operations specification
12
+ middleware.json # Middleware stack configuration
13
+ ```
14
+
15
+ ## Configuration Files
16
+
17
+ ### 1. config.json - Main Configuration
18
+
19
+ Primary service configuration with environment overrides:
20
+
21
+ ```json
22
+ {
23
+ "service": {
24
+ "name": "hello-service",
25
+ "version": "1.0.0",
26
+ "description": "Greeting service",
27
+ "environment": "${NODE_ENV:development}"
28
+ },
29
+ "server": {
30
+ "port": "${PORT:3000}",
31
+ "host": "${HOST:0.0.0.0}",
32
+ "timeout": 30000
33
+ },
34
+ "api": {
35
+ "versions": {
36
+ "available": ["v1"],
37
+ "current": "v1",
38
+ "deprecated": []
39
+ },
40
+ "rateLimit": {
41
+ "enabled": true,
42
+ "windowMs": 60000,
43
+ "max": 100
44
+ }
45
+ },
46
+ "monitoring": {
47
+ "healthCheck": {
48
+ "interval": 30000,
49
+ "timeout": 5000
50
+ },
51
+ "metrics": {
52
+ "enabled": "${METRICS_ENABLED:true}",
53
+ "port": "${METRICS_PORT:9090}"
54
+ }
55
+ },
56
+ "dependencies": {
57
+ "rabbitmq": {
58
+ "url": "${RABBITMQ_URL:amqp://localhost:5672}",
59
+ "enabled": "${MQ_ENABLED:true}"
60
+ },
61
+ "redis": {
62
+ "url": "${REDIS_URL:redis://localhost:6379}",
63
+ "enabled": "${CACHE_ENABLED:false}"
64
+ }
65
+ }
66
+ }
67
+ ```
68
+
69
+ ### 2. operations.json - Service Operations
70
+
71
+ Defines all operations the service provides:
72
+
73
+ ```json
74
+ {
75
+ "operations": {
76
+ "create-greeting": {
77
+ "description": "Generate a greeting message",
78
+ "handler": "handlers.greetings.create",
79
+ "endpoint": "/api/create-greeting",
80
+ "method": "POST",
81
+ "input": {
82
+ "name": {
83
+ "type": "string",
84
+ "required": true,
85
+ "description": "Name to greet"
86
+ }
87
+ },
88
+ "output": {
89
+ "message": {
90
+ "type": "string",
91
+ "description": "Generated greeting"
92
+ },
93
+ "timestamp": {
94
+ "type": "datetime"
95
+ }
96
+ }
97
+ }
98
+ }
99
+ }
100
+ ```
101
+
102
+ ### 3. middleware.json - Middleware Configuration
103
+
104
+ Middleware stack and configuration:
105
+
106
+ ```json
107
+ {
108
+ "global": [
109
+ {
110
+ "name": "cors",
111
+ "enabled": true,
112
+ "config": {
113
+ "origin": "${CORS_ORIGIN:*}",
114
+ "credentials": true
115
+ }
116
+ },
117
+ {
118
+ "name": "helmet",
119
+ "enabled": true,
120
+ "config": {}
121
+ },
122
+ {
123
+ "name": "requestLogger",
124
+ "enabled": true,
125
+ "config": {
126
+ "level": "info"
127
+ }
128
+ },
129
+ {
130
+ "name": "bodyParser",
131
+ "enabled": true,
132
+ "config": {
133
+ "limit": "10mb"
134
+ }
135
+ }
136
+ ],
137
+ "routes": {
138
+ "authenticate": {
139
+ "handler": "middleware/auth.authenticate",
140
+ "config": {
141
+ "required": true
142
+ }
143
+ },
144
+ "authorize": {
145
+ "handler": "middleware/auth.authorize",
146
+ "config": {
147
+ "roles": ["admin", "user"]
148
+ }
149
+ },
150
+ "validate": {
151
+ "handler": "middleware/validation.validate"
152
+ },
153
+ "rateLimit": {
154
+ "handler": "middleware/rateLimit",
155
+ "config": {
156
+ "max": 100,
157
+ "windowMs": 60000
158
+ }
159
+ }
160
+ },
161
+ "error": [
162
+ {
163
+ "name": "notFound",
164
+ "handler": "middleware/errors.notFound"
165
+ },
166
+ {
167
+ "name": "errorHandler",
168
+ "handler": "middleware/errors.handler"
169
+ }
170
+ ]
171
+ }
172
+ ```
173
+
174
+
175
+ ## Environment Variables
176
+
177
+ Configuration supports environment variable substitution:
178
+
179
+ - Format: `${VARIABLE_NAME:default_value}`
180
+ - Example: `${PORT:3000}` uses PORT env var or defaults to 3000
181
+
182
+ ### Standard Environment Variables
183
+
184
+ | Variable | Purpose | Default |
185
+ |----------|---------|---------|
186
+ | `NODE_ENV` | Environment (development/production) | development |
187
+ | `SERVICE_NAME` | Service name | From config.json |
188
+ | `PORT` | Server port | 3000 |
189
+ | `LOG_LEVEL` | Logging level | info |
190
+ | `RABBITMQ_URL` | RabbitMQ connection | amqp://localhost:5672 |
191
+ | `REDIS_URL` | Redis connection | redis://localhost:6379 |
192
+ | `METRICS_ENABLED` | Enable metrics | true |
193
+
194
+ ## Loading Configuration
195
+
196
+ Service wrapper automatically loads configuration:
197
+
198
+ ```javascript
199
+ const ServiceWrapper = require('@onlineapps/service-wrapper');
200
+
201
+ // Automatically loads from ./conn-config/
202
+ const wrapper = new ServiceWrapper();
203
+
204
+ // Or specify custom path
205
+ const wrapper = new ServiceWrapper({
206
+ configPath: './custom-config/'
207
+ });
208
+
209
+ // Access configuration
210
+ const config = wrapper.config;
211
+ console.log(config.service.name);
212
+ ```
213
+
214
+ ## Validation
215
+
216
+ Configuration is validated on startup:
217
+
218
+ 1. Required files exist
219
+ 2. JSON syntax is valid
220
+ 3. Required fields are present
221
+ 4. Environment variables are resolved
222
+ 5. Operations schema is valid
223
+
224
+ ## Best Practices
225
+
226
+ 1. **Keep sensitive data in environment variables** - Never commit secrets
227
+ 2. **Use defaults** - Provide sensible defaults for all configs
228
+ 3. **Document all options** - Include descriptions in configs
229
+ 4. **Validate early** - Fail fast on invalid configuration
230
+ 5. **Version your configs** - Track configuration changes
231
+
232
+ ## Service Configuration Example
233
+
234
+ ### config.json with Execution Mode
235
+ ```json
236
+ {
237
+ "service": {
238
+ "name": "hello-service",
239
+ "version": "1.0.0",
240
+ "execution": {
241
+ "mode": "${EXECUTION_MODE:direct}",
242
+ "direct": {
243
+ "handler": "./src/handlers"
244
+ },
245
+ "http": {
246
+ "baseUrl": "${SERVICE_URL:http://localhost:3000}"
247
+ }
248
+ }
249
+ },
250
+ "monitoring": {
251
+ "healthCheck": {
252
+ "interval": 30000
253
+ }
254
+ }
255
+ }
256
+ ```
257
+
258
+ ### Execution Modes
259
+
260
+ - **direct**: Service Wrapper calls handlers directly (50% memory savings)
261
+ - **http**: Service Wrapper makes HTTP calls (for external services)
@@ -0,0 +1,271 @@
1
+ # Service Wrapper - Final Architecture Decision
2
+
3
+ ## Executive Summary
4
+
5
+ Service Wrapper is a **collection of connectors** that provides all infrastructure components necessary for business services to function within the OA Drive system. It operates as a **single process architecture** where wrapper components run embedded within the service process.
6
+
7
+ ## Core Principles
8
+
9
+ 1. **Component Collection** - Service Wrapper is NOT a framework but a set of reusable connector components
10
+ 2. **Single Process** - All components run in the same process as the business service
11
+ 3. **Express + HTTP** - Business services remain standard Express applications
12
+ 4. **MQ-to-HTTP Proxy** - Wrapper listens on RabbitMQ and makes local HTTP calls
13
+ 5. **Zero Infrastructure in Services** - Services contain ONLY business logic
14
+
15
+ ## Architecture Decision
16
+
17
+ ### Why HTTP Pattern Over Handler Pattern
18
+
19
+ Despite handler pattern being **3.4x faster** (2.1ms vs 7.1ms) and using **67% less memory** (60MB vs 100MB), we chose the HTTP pattern because:
20
+
21
+ #### Handler Pattern Fatal Issues ❌
22
+ - **Node modules conflicts** - Service needs mongoose 5.x, wrapper needs 6.x = CONFLICT
23
+ - **Database connections broken** - Can't maintain connection pools
24
+ - **Third-party integration failures** - AWS SDK version conflicts
25
+ - **Testing becomes impossible** - Can't test service independently
26
+
27
+ #### HTTP Pattern Benefits ✅
28
+ - **100% compatibility** - All existing services work unchanged
29
+ - **Standard patterns** - All Express tooling works
30
+ - **Full functionality** - Databases, third-party services all work
31
+ - **Simple testing** - Service can run standalone
32
+ - **Acceptable overhead** - 5ms per request is negligible
33
+
34
+ ### Verdict
35
+ For typical service with 100 req/s:
36
+ - Performance difference: 500ms spread across 100 requests = **5ms per request**
37
+ - **5ms overhead is acceptable price for working solution!**
38
+
39
+ ## Implementation Architecture
40
+
41
+ ### Service Structure
42
+
43
+ ```
44
+ hello-service/
45
+ ├── src/
46
+ │ ├── app.js # Express app - business logic only
47
+ │ ├── routes/ # Business endpoints
48
+ │ └── handlers/ # Business logic
49
+ ├── conn-config/ # Wrapper configuration
50
+ │ ├── config.json # Service & wrapper config
51
+ │ └── operations.json # Operation to endpoint mapping
52
+ ├── index.js # Main entry point (initializes wrapper)
53
+ ├── package.json # Dependencies including @onlineapps/service-wrapper
54
+ └── .env # Environment variables
55
+ ```
56
+
57
+ ### Runtime Flow
58
+
59
+ ```javascript
60
+ // index.js - Service entry point
61
+ const express = require('express');
62
+ const { ServiceWrapper } = require('@onlineapps/service-wrapper');
63
+ const app = require('./src/app');
64
+
65
+ async function start() {
66
+ // 1. Start Express server
67
+ const server = app.listen(PORT);
68
+
69
+ // 2. Initialize wrapper components
70
+ const wrapper = new ServiceWrapper({
71
+ app,
72
+ server,
73
+ config: require('./conn-config/config.json'),
74
+ operations: require('./conn-config/operations.json')
75
+ });
76
+
77
+ await wrapper.initialize();
78
+ // Service now has all infrastructure components!
79
+ }
80
+ ```
81
+
82
+ ### Message Processing
83
+
84
+ #### HTTP Request Flow
85
+ ```
86
+ Client → HTTP → Express Router → Handler → Response
87
+
88
+ MonitoringConnector (metrics)
89
+ ```
90
+
91
+ #### MQ Message Flow
92
+ ```
93
+ RabbitMQ → MQConnector → Parse operations.json → HTTP localhost:3000/api/endpoint
94
+
95
+ Express Router → Handler
96
+
97
+ Response → MQ
98
+ ```
99
+
100
+ ## Component Architecture
101
+
102
+ ### Service Wrapper Components
103
+
104
+ 1. **MQConnector** - RabbitMQ integration
105
+ - Listens on `workflow.init` queue
106
+ - Listens on `{service-name}.workflow` queue
107
+ - Routes messages based on operations.json
108
+
109
+ 2. **MonitoringConnector** - Metrics collection
110
+ - Request tracking
111
+ - Performance metrics
112
+ - Error rates
113
+
114
+ 3. **HealthConnector** - Health checks
115
+ - Provides `/health` endpoint
116
+ - Aggregates component status
117
+ - Custom health check support
118
+
119
+ 4. **RegistryConnector** - Service discovery
120
+ - Registers service on startup
121
+ - Sends heartbeat
122
+ - Updates capabilities
123
+
124
+ ## Operations Schema
125
+
126
+ Replaces OpenAPI with simpler format optimized for workflow processing:
127
+
128
+ ```json
129
+ {
130
+ "operations": {
131
+ "operation-name": {
132
+ "description": "Human-readable description",
133
+ "endpoint": "/api/operation-name",
134
+ "method": "POST",
135
+ "input": {
136
+ "field1": { "type": "string", "required": true }
137
+ },
138
+ "output": {
139
+ "result": { "type": "string" }
140
+ }
141
+ }
142
+ }
143
+ }
144
+ ```
145
+
146
+ ## Benefits of This Architecture
147
+
148
+ ### For Development
149
+ - **Zero infrastructure code** in services
150
+ - **Standard Express patterns** work
151
+ - **Simple debugging** - one process, one log stream
152
+ - **Easy testing** - service runs standalone
153
+
154
+ ### For Operations
155
+ - **Simple deployment** - one process per service
156
+ - **Central management** - update wrapper version for all
157
+ - **Graceful shutdown** - wrapper handles cleanup
158
+ - **No message loss** - RabbitMQ persistent queues
159
+
160
+ ### For Performance
161
+ - **5ms overhead** - acceptable for real-world use
162
+ - **Efficient resource usage** - shared memory in single process
163
+ - **Connection pooling** - wrapper manages MQ connections
164
+ - **Horizontal scaling** - just add more service instances
165
+
166
+ ## What Services DON'T Handle
167
+
168
+ - ❌ RabbitMQ connection management
169
+ - ❌ Queue subscription logic
170
+ - ❌ Message parsing and validation
171
+ - ❌ Service discovery registration
172
+ - ❌ Health check implementation
173
+ - ❌ Monitoring middleware
174
+ - ❌ Retry and error handling
175
+
176
+ **All handled by Service Wrapper components!**
177
+
178
+ ## Migration Strategy
179
+
180
+ ### For New Services
181
+ 1. Create Express app with business logic
182
+ 2. Add `conn-config/operations.json`
183
+ 3. Add Service Wrapper dependency
184
+ 4. Create `index.js` entry point
185
+ 5. Deploy
186
+
187
+ ### For Existing Services
188
+ 1. Keep all existing code unchanged
189
+ 2. Add configuration files
190
+ 3. Wrap with Service Wrapper
191
+ 4. Remove infrastructure code
192
+ 5. Deploy - no breaking changes!
193
+
194
+ ## Configuration
195
+
196
+ ### Service Configuration (conn-config/config.json)
197
+ ```json
198
+ {
199
+ "service": {
200
+ "name": "hello-service",
201
+ "version": "1.0.0",
202
+ "port": 3000
203
+ },
204
+ "wrapper": {
205
+ "mq": {
206
+ "url": "${RABBITMQ_URL}",
207
+ "prefetch": 10
208
+ },
209
+ "monitoring": {
210
+ "enabled": true
211
+ },
212
+ "health": {
213
+ "endpoint": "/health"
214
+ },
215
+ "registry": {
216
+ "url": "${REGISTRY_URL}"
217
+ }
218
+ }
219
+ }
220
+ ```
221
+
222
+ ## Testing Strategy
223
+
224
+ ### Unit Tests (without wrapper)
225
+ ```javascript
226
+ const app = require('./src/app');
227
+ const request = require('supertest');
228
+
229
+ test('business logic', async () => {
230
+ const res = await request(app).post('/api/operation');
231
+ expect(res.status).toBe(200);
232
+ });
233
+ ```
234
+
235
+ ### Integration Tests (with wrapper)
236
+ ```javascript
237
+ const { start } = require('./index');
238
+
239
+ beforeAll(async () => {
240
+ await start();
241
+ });
242
+
243
+ test('full service', async () => {
244
+ // Test with all infrastructure
245
+ });
246
+ ```
247
+
248
+ ## Performance Characteristics
249
+
250
+ | Metric | Value | Acceptable? |
251
+ |--------|-------|-------------|
252
+ | Added latency | 5ms per request | ✅ Yes |
253
+ | Memory overhead | 40MB per service | ✅ Yes |
254
+ | CPU overhead | 4% per 1000 req/s | ✅ Yes |
255
+ | Startup time | +2 seconds | ✅ Yes |
256
+
257
+ ## Conclusion
258
+
259
+ This architecture provides the **optimal balance** between:
260
+ - **Simplicity** - Single process, standard patterns
261
+ - **Compatibility** - Works with all existing services
262
+ - **Performance** - Acceptable overhead for massive benefits
263
+ - **Maintainability** - Central management, no duplication
264
+
265
+ The 5ms latency overhead is a **small price** for:
266
+ - 100% compatibility
267
+ - Zero infrastructure code in services
268
+ - Central management of all components
269
+ - Full functionality including databases
270
+
271
+ **This is the final, production-ready architecture for Service Wrapper.**