@vptech/ts-apigateway-validator
v1.0.0
Published
Pure TypeScript library to automatically generate AWS API Gateway request validators from TypeScript interfaces
Downloads
5
Readme
TypeScript to AWS API Gateway Validator
A pure TypeScript library that automatically generates AWS API Gateway request validators from TypeScript interfaces. Eliminate manual JSON Schema creation and ensure type-safe API validation with zero runtime dependencies.
Features
✅ Zero Runtime Dependencies - Pure TypeScript implementation
✅ Type-Safe - Automatic alignment between TS interfaces and API validation
✅ JSDoc Integration - Extract validation constraints from comments
✅ AWS CDK Ready - Direct integration with CDK constructs
✅ Medical Compliance - Built for Australian healthcare standards
✅ Comprehensive - Supports complex types, arrays, unions, nested objects
✅ Fast - Validation happens at API Gateway (before Lambda invocation)
Installation
npm install @vptech/ts-apigateway-validatorPeer Dependencies
npm install aws-cdk-lib constructs typescriptQuick Start
1. Define Your TypeScript Interface
// types/user.ts
export interface CreateUserRequest {
/**
* User's email address
* @format email
* @maxLength 254
*/
email: string;
/**
* User's full name
* @minLength 2
* @maxLength 100
*/
name: string;
/**
* User's age
* @minimum 18
* @maximum 120
*/
age?: number;
/** User's preferred language */
language?: 'en' | 'es' | 'fr' | 'de';
}2. Generate Validator
import { generateValidator } from '@vptech/ts-apigateway-validator';
const validator = generateValidator({
sourceFile: './types/user.ts',
interfaceName: 'CreateUserRequest',
validationLevel: 'strict'
});
console.log(validator.jsonSchema);
// Outputs JSON Schema Draft 4 compatible with API Gateway3. Integrate with AWS CDK
import * as apigateway from 'aws-cdk-lib/aws-apigateway';
import { generateValidator } from '@vptech/ts-apigateway-validator';
export class UserApiStack extends Stack {
constructor(scope: Construct, id: string, props?: StackProps) {
super(scope, id, props);
const api = new apigateway.RestApi(this, 'UserApi');
// Generate validator from TypeScript interface
const validator = generateValidator({
sourceFile: './types/user.ts',
interfaceName: 'CreateUserRequest',
validationLevel: 'strict'
});
// Create CDK model and request validator
const userModel = validator.createModel(this, api, 'UserModel');
const requestValidator = validator.createValidator(this, 'UserValidator')(api);
// Add API method with automatic validation
const users = api.root.addResource('users');
users.addMethod('POST', new apigateway.LambdaIntegration(userLambda), {
requestModels: {
'application/json': userModel
},
requestValidator: requestValidator
});
}
}API Reference
Core Functions
generateValidator(config: ValidatorConfig): ValidationResult
Main function to generate API Gateway validators from TypeScript interfaces.
interface ValidatorConfig {
sourceFile: string; // Path to TypeScript file
interfaceName: string; // Interface name to validate
validationLevel?: 'strict' | 'permissive'; // Validation strictness
customValidators?: Record<string, ValidationFunction>; // Custom validation
additionalProperties?: Record<string, any>; // Extra JSON Schema properties
}createValidatorFromInterface<T>(sourceFile, interfaceName, options?): ValidationResult
Convenience function for quick validator generation.
listAvailableInterfaces(sourceFile: string): string[]
Lists all interfaces available in a TypeScript file.
CDK Integration
ValidationFactory.createValidationSetup(scope, api, jsonSchema, options?)
Creates complete validation setup for CDK API Gateway methods.
const setup = ValidationFactory.createValidationSetup(scope, api, jsonSchema, {
modelName: 'UserModel',
validatorName: 'UserValidator'
});
// Use in API Gateway method
resource.addMethod('POST', integration, setup.methodOptions);JSDoc Validation Constraints
Use JSDoc comments to add validation constraints to your TypeScript interfaces:
String Validation
interface Example {
/**
* @minLength 1
* @maxLength 100
* @pattern ^[a-zA-Z]+$
* @format email
*/
email: string;
}Number Validation
interface Example {
/**
* @minimum 0
* @maximum 100
* @multipleOf 5
*/
score: number;
}Array Validation
interface Example {
/**
* @minItems 1
* @maxItems 10
* @uniqueItems
*/
tags: string[];
}Supported Formats
email- Email address validationdate- ISO date format (YYYY-MM-DD)date-time- ISO datetime formaturi- URI validationuuid- UUID validation
Medical API Example
Perfect for Australian healthcare applications:
// patient.ts
export interface CreatePatientRequest {
patientId: string;
/**
* Patient's first name
* @minLength 1
* @maxLength 100
*/
firstName: string;
/**
* Date of birth (ISO format)
* @format date
*/
dob?: string;
/**
* Email address
* @format email
* @maxLength 254
*/
email?: string;
/**
* Australian phone number
* @pattern ^(\+61|0)[2-9][0-9]{8}$
*/
phone?: string;
/**
* Australian state
*/
state?: 'NSW' | 'VIC' | 'QLD' | 'WA' | 'SA' | 'TAS' | 'NT' | 'ACT';
/**
* Australian Medicare number
* @pattern ^[0-9]{10}[0-9]?$
*/
medicareNumber?: string;
}Advanced Usage
Factory Pattern
import { createValidatorFactory } from '@vptech/ts-apigateway-validator';
// Create factory with common configuration
const medicalValidatorFactory = createValidatorFactory({
sourceFile: './types/medical.ts',
validationLevel: 'strict',
additionalProperties: {
'$comment': 'Generated for Australian medical system'
}
});
// Generate validators for different interfaces
const patientValidator = medicalValidatorFactory('CreatePatientRequest');
const appointmentValidator = medicalValidatorFactory('CreateAppointmentRequest');Custom Validation
const validator = generateValidator({
sourceFile: './types/user.ts',
interfaceName: 'User',
customValidators: {
'email': (value) => value.endsWith('@company.com') || 'Must be company email',
'age': (value) => value >= 21 || 'Must be 21 or older'
}
});Integration with Existing Controllers
import { generateValidator } from '@vptech/ts-apigateway-validator';
export class PatientController extends Construct {
constructor(scope: Construct, id: string, props: PatientControllerProps) {
super(scope, id);
// Replace manual JSON Schema with automatic generation
const createPatientValidator = generateValidator({
sourceFile: './models/patient.ts',
interfaceName: 'CreatePatientRequest',
validationLevel: 'strict'
});
const updatePatientValidator = generateValidator({
sourceFile: './models/patient.ts',
interfaceName: 'UpdatePatientRequest',
validationLevel: 'permissive'
});
// Create CDK models
const createModel = createPatientValidator.createModel(this, props.api);
const updateModel = updatePatientValidator.createModel(this, props.api);
const requestValidator = createPatientValidator.createValidator(this)(props.api);
// Add methods with validation
this.patientsResource.addMethod('POST', lambdaIntegration, {
...props.defaultOptions,
requestModels: { 'application/json': createModel },
requestValidator: requestValidator
});
}
}Supported TypeScript Features
✅ Primitive Types: string, number, boolean, null, undefined
✅ Complex Types: interfaces, type aliases, nested objects
✅ Arrays: T[], Array, with element type validation
✅ Unions: String literal unions → enums, nullable types
✅ Optional Properties: Handled correctly in required arrays
✅ Inheritance: extends keyword support
✅ JSDoc: Comprehensive constraint extraction
✅ Generic Types: Basic generic type resolution
AWS API Gateway Compatibility
The library generates JSON Schema Draft 4 compatible with AWS API Gateway:
- ✅ String validation (length, pattern, format)
- ✅ Number validation (min, max, multipleOf)
- ✅ Array validation (minItems, maxItems, uniqueItems)
- ✅ Object validation (properties, required, additionalProperties)
- ✅ Enum validation (string literal unions)
- ⚠️ Limited support for oneOf/anyOf (API Gateway restriction)
- ❌ $ref references not supported in inline schemas
Error Handling
try {
const validator = generateValidator({
sourceFile: './types/user.ts',
interfaceName: 'NonExistentInterface',
validationLevel: 'strict'
});
} catch (error) {
console.error('Validation generation failed:', error.message);
// Handle error appropriately
}Performance Benefits
- Reduced Lambda Invocations: Invalid requests rejected at API Gateway
- Lower Costs: No Lambda execution for validation errors
- Faster Response: Immediate validation feedback
- Better Security: Consistent validation before business logic
Migration from Manual Schemas
Before (Manual JSON Schema)
const patientModel = new apigateway.Model(scope, 'PatientModel', {
schema: {
schema: apigateway.JsonSchemaVersion.DRAFT4,
type: apigateway.JsonSchemaType.OBJECT,
properties: {
firstName: {
type: apigateway.JsonSchemaType.STRING,
minLength: 1,
maxLength: 100
},
// ... 50 more lines of manual schema
},
required: ['firstName', 'lastName']
}
});After (Automatic Generation)
const validator = generateValidator({
sourceFile: './models/patient.ts',
interfaceName: 'CreatePatientRequest'
});
const patientModel = validator.createModel(scope, api);Contributing
- Fork the repository
- Create your feature branch (
git checkout -b feature/amazing-feature) - Add tests for your changes
- Run the test suite (
npm test) - Commit your changes (
git commit -m 'Add amazing feature') - Push to the branch (
git push origin feature/amazing-feature) - Open a Pull Request
Testing
# Run all tests
npm test
# Run tests with coverage
npm test -- --coverage
# Run tests in watch mode
npm test -- --watch
# Run integration tests only
npm test -- integration.test.tsLicense
MIT License - see the LICENSE file for details.
Support
- 📧 Email: [email protected]
- 🐛 Issues: GitHub Issues
- 📖 Documentation: Full API Docs
Changelog
v1.0.0
- Initial release with TypeScript interface parsing
- JSON Schema generation for API Gateway
- CDK integration helpers
- Comprehensive test suite
- Medical API examples for Australian healthcare
Made with ❤️ for the TypeScript and AWS CDK community
