serverless-plugin-module-registry 1.0.4 → 1.0.6

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 CHANGED
@@ -120,6 +120,10 @@ The plugin creates an **intermodular** `ModuleRegistry` table using **AWS SDK v3
120
120
  - **GSI1PK**: `MODULES` (for listing all modules)
121
121
  - **GSI1SK**: `MODULE#{moduleName}` (for grouping by module)
122
122
 
123
+ ### Global Secondary Index (GSI2)
124
+ - **GSI2PK**: `FEATURES` (for listing all features)
125
+ - **GSI2SK**: `FEATURE#{featureId}` (for direct feature lookup by ID)
126
+
123
127
  ### Data Structure
124
128
  ```json
125
129
  {
@@ -188,6 +192,19 @@ const feature = await dynamoClient.getItem({
188
192
  })
189
193
  ```
190
194
 
195
+ ### Get Feature by ID (GSI2)
196
+ ```javascript
197
+ // Query GSI2 with featureId
198
+ const feature = await dynamoClient.query({
199
+ IndexName: 'GSI2',
200
+ KeyConditionExpression: 'GSI2PK = :pk AND GSI2SK = :sk',
201
+ ExpressionAttributeValues: {
202
+ ':pk': 'FEATURES',
203
+ ':sk': `FEATURE#${featureId}`
204
+ }
205
+ })
206
+ ```
207
+
191
208
  ## ⚙️ Configuration Options
192
209
 
193
210
  | Option | Type | Default | Description |
@@ -262,15 +279,15 @@ Example output:
262
279
 
263
280
  ### TypeScript/ES6 Imports
264
281
  ```typescript
265
- // In your handlers
266
- import {
267
- listAllModules,
268
- getModuleFeatures,
282
+ // In your handlers - import from the generated service package
283
+ import {
284
+ listAllModules,
285
+ getModuleFeatures,
269
286
  getFeatureDetails,
270
287
  createModuleRegistryLogger,
271
288
  type ModuleInfo,
272
289
  type FeatureInfo
273
- } from 'serverless-plugin-module-registry'
290
+ } from 'module-registry'
274
291
 
275
292
  const logger = createModuleRegistryLogger('my-handler')
276
293
 
@@ -279,16 +296,28 @@ export const myHandler = async (event: any) => {
279
296
  logger.info(`Found ${modules.length} modules`)
280
297
  return { modules }
281
298
  }
299
+
300
+ // Example: Get feature by ID without knowing module
301
+ export const getFeatureHandler = async (event: any) => {
302
+ const { featureId } = event.pathParameters
303
+ const feature = await getFeatureById(featureId)
304
+
305
+ if (!feature) {
306
+ return { statusCode: 404, body: { error: 'Feature not found' } }
307
+ }
308
+
309
+ return { statusCode: 200, body: feature }
310
+ }
282
311
  ```
283
312
 
284
313
  ### CommonJS/Node.js Require
285
314
  ```javascript
286
- // In your handlers
287
- const {
288
- listAllModules,
289
- getModuleFeatures,
290
- createModuleRegistryLogger
291
- } = require('serverless-plugin-module-registry')
315
+ // In your handlers - require from the generated service package
316
+ const {
317
+ listAllModules,
318
+ getModuleFeatures,
319
+ createModuleRegistryLogger
320
+ } = require('module-registry')
292
321
 
293
322
  const logger = createModuleRegistryLogger('my-handler')
294
323
 
@@ -306,6 +335,7 @@ exports.myHandler = async (event) => {
306
335
  | `listAllModules()` | List all deployed modules | `Promise<ModuleInfo[]>` |
307
336
  | `getModuleFeatures(moduleName)` | Get features for a module | `Promise<FeatureInfo[]>` |
308
337
  | `getFeatureDetails(moduleName, featureName)` | Get feature details | `Promise<FeatureDetails \| null>` |
338
+ | `getFeatureById(featureId)` | Get feature by ID only (uses GSI2) | `Promise<FeatureDetails \| null>` |
309
339
  | `getModuleMetadata(moduleName)` | Get module metadata only | `Promise<ModuleInfo \| null>` |
310
340
  | `getAllEndpoints()` | Get all endpoints across modules | `Promise<EndpointInfo[]>` |
311
341
  | `createModuleRegistryLogger(context)` | Create logger for service functions | `Logger` |
@@ -351,6 +381,222 @@ export const listModules = http(async (event) => {
351
381
  })
352
382
  ```
353
383
 
384
+ ## 🚀 CLI Commands
385
+
386
+ The plugin provides powerful CLI commands for managing module registries:
387
+
388
+ ### Generate Registry with AI (`registryGenerate`)
389
+
390
+ Automatically generate registry files for a module using AI analysis:
391
+
392
+ ```bash
393
+ # Generate registry for a specific module
394
+ serverless registryGenerate --module workforce
395
+
396
+ # Force overwrite existing registry files
397
+ serverless registryGenerate --module workforce --force
398
+ ```
399
+
400
+ **Prerequisites:**
401
+ - Set `OPENROUTER_API_KEY` environment variable for AI generation
402
+ - Module must have function descriptions in serverless function definitions
403
+ - Only functions with `aws_iam` authorizer are included in registry
404
+
405
+ **What it does:**
406
+ 1. Analyzes module structure (functions, resources, endpoints)
407
+ 2. Uses AI (Claude 3.5 Sonnet) to generate AWS-style feature groupings
408
+ 3. Creates `registry/module.yml` and `registry/features/*.yml` files
409
+ 4. Follows AWS IAM naming conventions (e.g., `EmployeeReadAccess`, `UserSelfService`)
410
+
411
+ ### Generate Service Package (`registryGeneratePackage`)
412
+
413
+ Generate the virtual service package for importing registry functions:
414
+
415
+ ```bash
416
+ # Generate service package
417
+ serverless registryGeneratePackage
418
+
419
+ # Force regeneration
420
+ serverless registryGeneratePackage --force --verbose
421
+ ```
422
+
423
+ **What it creates:**
424
+ - `node_modules/module-registry/service.js` - Service functions
425
+ - `node_modules/module-registry/service.d.ts` - TypeScript definitions
426
+ - `node_modules/module-registry/env.js` - Environment configuration
427
+ - `node_modules/module-registry/package.json` - Package manifest
428
+
429
+ ## 🛠️ Development
430
+
431
+ ### Prerequisites
432
+
433
+ - Node.js ≥14.0.0
434
+ - TypeScript ≥5.0
435
+ - Serverless Framework ≥2.0.0
436
+
437
+ ### Setup
438
+
439
+ ```bash
440
+ # Install dependencies
441
+ npm install
442
+
443
+ # Build the plugin
444
+ npm run build
445
+
446
+ # Watch for changes during development
447
+ npm run watch
448
+
449
+ # Run type checking
450
+ npm run typecheck
451
+
452
+ # Run linting
453
+ npm run lint
454
+ ```
455
+
456
+ ### Build Configuration
457
+
458
+ The project uses [tsup](https://tsup.egoist.dev/) for building:
459
+
460
+ - **Entry**: `src/index.ts` (main plugin), `src/service.ts` (service functions)
461
+ - **Output**: `dist/` directory with CommonJS and TypeScript definitions
462
+ - **Target**: Node.js 14+ compatibility
463
+ - **External**: Serverless Framework excluded from bundle
464
+
465
+ ### Testing
466
+
467
+ Tests are currently disabled but the framework is set up with Jest:
468
+
469
+ ```bash
470
+ # Tests are disabled - would run with:
471
+ npm test # Currently outputs: "Tests disabled"
472
+ ```
473
+
474
+ ## 🔧 Troubleshooting
475
+
476
+ ### Common Issues
477
+
478
+ **Plugin not found**
479
+ ```
480
+ Error: Plugin "serverless-plugin-module-registry" not found
481
+ ```
482
+ Solution: Ensure plugin is installed and listed in `serverless.yml` plugins section
483
+
484
+ **Variable resolution errors**
485
+ ```
486
+ Module Registry: Unresolved variables in configuration
487
+ ```
488
+ Solution: Check that all variables in `custom.moduleRegistry` section can be resolved
489
+
490
+ **DynamoDB table creation fails**
491
+ ```
492
+ Failed to create table: AccessDenied
493
+ ```
494
+ Solution: Ensure AWS credentials have DynamoDB permissions:
495
+ - `dynamodb:CreateTable`
496
+ - `dynamodb:DescribeTable`
497
+ - `dynamodb:UpdateContinuousBackups`
498
+ - `dynamodb:TagResource`
499
+
500
+ **AI generation fails**
501
+ ```
502
+ OPENROUTER_API_KEY environment variable is required
503
+ ```
504
+ Solution: Set OpenRouter API key: `export OPENROUTER_API_KEY=your_key_here`
505
+
506
+ **Registry generation requires function descriptions**
507
+ ```
508
+ Function 'myFunction' is missing required 'description' field
509
+ ```
510
+ Solution: Add descriptions to all functions in your serverless function definitions
511
+
512
+ ### Debug Mode
513
+
514
+ Enable detailed logging:
515
+
516
+ ```bash
517
+ serverless deploy --verbose
518
+ ```
519
+
520
+ Look for `[module-registry]` prefixed logs for plugin-specific information.
521
+
522
+ ## 📊 Performance Considerations
523
+
524
+ ### DynamoDB Costs
525
+
526
+ - Plugin creates one table per service/stage combination
527
+ - Uses **Pay-Per-Request** billing mode
528
+ - Table persists across deployments (not recreated)
529
+ - Point-in-time recovery enabled by default
530
+
531
+ ### Batch Operations
532
+
533
+ - Registry updates use batch writes (25 items per batch)
534
+ - Automatic cleanup of stale entries during deployment
535
+ - Optimized for sparse access patterns
536
+
537
+ ### CloudFormation Policies
538
+
539
+ - IAM policies generated as CloudFormation resources
540
+ - Policy ARNs resolved at deployment time
541
+ - No runtime AWS API calls for policy management
542
+
543
+ ## 🔒 Security Considerations
544
+
545
+ ### IAM Policies
546
+
547
+ - Generated policies follow **least privilege** principle
548
+ - Endpoint-specific resource ARNs (not wildcards)
549
+ - Custom policies allow fine-grained permission control
550
+
551
+ ### Access Control
552
+
553
+ - Registry table access requires DynamoDB permissions
554
+ - Cross-module access controlled via IAM policy ARNs
555
+ - Service functions inherit Lambda execution role permissions
556
+
557
+ ### Best Practices
558
+
559
+ 1. **Review generated policies** before deployment
560
+ 2. **Use strict mode** (`strict: true`) in production
561
+ 3. **Regularly audit** endpoint permissions
562
+ 4. **Implement proper** IAM role boundaries
563
+
564
+ ## 🤝 Contributing
565
+
566
+ ### Development Workflow
567
+
568
+ 1. Fork the repository
569
+ 2. Create a feature branch: `git checkout -b feature/my-feature`
570
+ 3. Make changes and test thoroughly
571
+ 4. Update documentation if needed
572
+ 5. Submit a pull request
573
+
574
+ ### Code Standards
575
+
576
+ - Follow TypeScript best practices
577
+ - Use provided ESLint configuration
578
+ - Add JSDoc comments for public APIs
579
+ - Maintain backward compatibility
580
+
581
+ ### Testing
582
+
583
+ When contributing:
584
+ - Add test cases for new features
585
+ - Ensure existing functionality isn't broken
586
+ - Test with multiple Serverless Framework versions
587
+
588
+ ## 📋 Version Compatibility
589
+
590
+ | Plugin Version | Serverless Framework | Node.js |
591
+ |----------------|---------------------|---------|
592
+ | 1.0.x | 2.x, 3.x, 4.x | ≥14.0 |
593
+
594
+ ### Serverless Framework Features
595
+
596
+ - **v2**: Basic hook support, CloudFormation resources
597
+ - **v3**: Enhanced variable resolution, improved logging
598
+ - **v4**: Full ESM support, performance optimizations
599
+
354
600
  ## 📄 License
355
601
 
356
602
  MIT License - see the [LICENSE](LICENSE) file for details.