omgkit 2.0.7 → 2.1.1

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.
Files changed (27) hide show
  1. package/package.json +2 -2
  2. package/plugin/skills/backend/api-architecture/SKILL.md +857 -0
  3. package/plugin/skills/backend/caching-strategies/SKILL.md +755 -0
  4. package/plugin/skills/backend/event-driven-architecture/SKILL.md +753 -0
  5. package/plugin/skills/backend/real-time-systems/SKILL.md +635 -0
  6. package/plugin/skills/databases/database-optimization/SKILL.md +571 -0
  7. package/plugin/skills/databases/postgresql/SKILL.md +494 -18
  8. package/plugin/skills/devops/docker/SKILL.md +466 -18
  9. package/plugin/skills/devops/monorepo-management/SKILL.md +595 -0
  10. package/plugin/skills/devops/observability/SKILL.md +622 -0
  11. package/plugin/skills/devops/performance-profiling/SKILL.md +905 -0
  12. package/plugin/skills/frameworks/nextjs/SKILL.md +407 -44
  13. package/plugin/skills/frameworks/react/SKILL.md +1006 -32
  14. package/plugin/skills/frontend/advanced-ui-design/SKILL.md +426 -0
  15. package/plugin/skills/integrations/ai-integration/SKILL.md +730 -0
  16. package/plugin/skills/integrations/payment-integration/SKILL.md +735 -0
  17. package/plugin/skills/languages/python/SKILL.md +489 -25
  18. package/plugin/skills/languages/typescript/SKILL.md +379 -30
  19. package/plugin/skills/methodology/problem-solving/SKILL.md +355 -0
  20. package/plugin/skills/methodology/research-validation/SKILL.md +668 -0
  21. package/plugin/skills/methodology/sequential-thinking/SKILL.md +260 -0
  22. package/plugin/skills/mobile/mobile-development/SKILL.md +756 -0
  23. package/plugin/skills/security/security-hardening/SKILL.md +633 -0
  24. package/plugin/skills/tools/document-processing/SKILL.md +916 -0
  25. package/plugin/skills/tools/image-processing/SKILL.md +748 -0
  26. package/plugin/skills/tools/mcp-development/SKILL.md +883 -0
  27. package/plugin/skills/tools/media-processing/SKILL.md +831 -0
@@ -0,0 +1,633 @@
1
+ ---
2
+ name: security-hardening
3
+ description: Advanced security patterns including zero-trust architecture, secret management, CSP, and compliance frameworks
4
+ category: security
5
+ triggers:
6
+ - security hardening
7
+ - zero trust
8
+ - secret management
9
+ - csp
10
+ - security headers
11
+ - compliance
12
+ - penetration testing
13
+ ---
14
+
15
+ # Security Hardening
16
+
17
+ Implement **advanced security patterns** beyond basic OWASP guidelines. This skill covers zero-trust architecture, secret management, security headers, and compliance frameworks.
18
+
19
+ ## Purpose
20
+
21
+ Build defense-in-depth for production systems:
22
+
23
+ - Implement zero-trust security model
24
+ - Manage secrets securely with Vault
25
+ - Configure comprehensive security headers
26
+ - Design Content Security Policy (CSP)
27
+ - Prepare for security audits
28
+ - Meet compliance requirements (SOC2, GDPR)
29
+
30
+ ## Features
31
+
32
+ ### 1. Zero-Trust Architecture
33
+
34
+ ```typescript
35
+ // Zero-trust middleware chain
36
+ import { Request, Response, NextFunction } from 'express';
37
+
38
+ // 1. Verify identity on every request
39
+ async function verifyIdentity(req: Request, res: Response, next: NextFunction) {
40
+ const token = extractToken(req);
41
+
42
+ if (!token) {
43
+ return res.status(401).json({ error: 'Authentication required' });
44
+ }
45
+
46
+ try {
47
+ // Verify token signature and expiration
48
+ const decoded = await verifyToken(token);
49
+
50
+ // Check if token is revoked
51
+ if (await isTokenRevoked(decoded.jti)) {
52
+ return res.status(401).json({ error: 'Token revoked' });
53
+ }
54
+
55
+ // Verify user still exists and is active
56
+ const user = await getUserById(decoded.sub);
57
+ if (!user || user.status !== 'active') {
58
+ return res.status(401).json({ error: 'User not found or inactive' });
59
+ }
60
+
61
+ req.user = user;
62
+ req.tokenClaims = decoded;
63
+ next();
64
+ } catch (error) {
65
+ return res.status(401).json({ error: 'Invalid token' });
66
+ }
67
+ }
68
+
69
+ // 2. Verify authorization for every action
70
+ async function verifyAuthorization(resource: string, action: string) {
71
+ return (req: Request, res: Response, next: NextFunction) => {
72
+ const allowed = checkPermission(req.user, resource, action);
73
+
74
+ if (!allowed) {
75
+ auditLog({
76
+ event: 'authorization_denied',
77
+ userId: req.user.id,
78
+ resource,
79
+ action,
80
+ ip: req.ip,
81
+ });
82
+
83
+ return res.status(403).json({ error: 'Access denied' });
84
+ }
85
+
86
+ next();
87
+ };
88
+ }
89
+
90
+ // 3. Verify device/context
91
+ async function verifyContext(req: Request, res: Response, next: NextFunction) {
92
+ const deviceFingerprint = req.headers['x-device-fingerprint'];
93
+ const geoLocation = await getGeoLocation(req.ip);
94
+
95
+ // Check for unusual patterns
96
+ const risk = await assessRisk({
97
+ userId: req.user.id,
98
+ deviceFingerprint,
99
+ geoLocation,
100
+ userAgent: req.headers['user-agent'],
101
+ timestamp: Date.now(),
102
+ });
103
+
104
+ if (risk.score > 0.8) {
105
+ // Require step-up authentication
106
+ return res.status(403).json({
107
+ error: 'Additional verification required',
108
+ challenge: risk.challengeType,
109
+ });
110
+ }
111
+
112
+ if (risk.score > 0.5) {
113
+ // Log suspicious activity
114
+ auditLog({
115
+ event: 'suspicious_activity',
116
+ userId: req.user.id,
117
+ riskScore: risk.score,
118
+ factors: risk.factors,
119
+ });
120
+ }
121
+
122
+ next();
123
+ }
124
+
125
+ // Apply zero-trust chain
126
+ app.use('/api', verifyIdentity, verifyContext);
127
+ app.get('/api/users/:id', verifyAuthorization('users', 'read'), getUser);
128
+ app.put('/api/users/:id', verifyAuthorization('users', 'write'), updateUser);
129
+ ```
130
+
131
+ ### 2. Secret Management with Vault
132
+
133
+ ```typescript
134
+ import Vault from 'node-vault';
135
+
136
+ class SecretManager {
137
+ private vault: Vault.client;
138
+ private cache: Map<string, { value: any; expires: number }> = new Map();
139
+ private cacheTTL = 300000; // 5 minutes
140
+
141
+ constructor() {
142
+ this.vault = Vault({
143
+ apiVersion: 'v1',
144
+ endpoint: process.env.VAULT_ADDR,
145
+ token: process.env.VAULT_TOKEN,
146
+ });
147
+ }
148
+
149
+ async getSecret(path: string): Promise<any> {
150
+ // Check cache
151
+ const cached = this.cache.get(path);
152
+ if (cached && cached.expires > Date.now()) {
153
+ return cached.value;
154
+ }
155
+
156
+ // Fetch from Vault
157
+ const response = await this.vault.read(`secret/data/${path}`);
158
+ const secret = response.data.data;
159
+
160
+ // Cache the secret
161
+ this.cache.set(path, {
162
+ value: secret,
163
+ expires: Date.now() + this.cacheTTL,
164
+ });
165
+
166
+ return secret;
167
+ }
168
+
169
+ async getDatabaseCredentials(): Promise<{ username: string; password: string }> {
170
+ // Dynamic database credentials
171
+ const response = await this.vault.read('database/creds/my-role');
172
+ return {
173
+ username: response.data.username,
174
+ password: response.data.password,
175
+ };
176
+ }
177
+
178
+ async rotateSecret(path: string, newValue: any): Promise<void> {
179
+ await this.vault.write(`secret/data/${path}`, {
180
+ data: newValue,
181
+ });
182
+
183
+ // Invalidate cache
184
+ this.cache.delete(path);
185
+ }
186
+
187
+ // AWS IAM credentials via Vault
188
+ async getAWSCredentials(): Promise<AWS.Credentials> {
189
+ const response = await this.vault.read('aws/creds/my-role');
190
+ return {
191
+ accessKeyId: response.data.access_key,
192
+ secretAccessKey: response.data.secret_key,
193
+ sessionToken: response.data.security_token,
194
+ };
195
+ }
196
+ }
197
+
198
+ // Environment variable encryption
199
+ import { createCipheriv, createDecipheriv, randomBytes, scrypt } from 'crypto';
200
+
201
+ async function encryptEnvFile(envContent: string, password: string): Promise<string> {
202
+ const salt = randomBytes(16);
203
+ const key = await new Promise<Buffer>((resolve, reject) => {
204
+ scrypt(password, salt, 32, (err, key) => {
205
+ if (err) reject(err);
206
+ else resolve(key);
207
+ });
208
+ });
209
+
210
+ const iv = randomBytes(16);
211
+ const cipher = createCipheriv('aes-256-gcm', key, iv);
212
+
213
+ let encrypted = cipher.update(envContent, 'utf8', 'hex');
214
+ encrypted += cipher.final('hex');
215
+
216
+ const authTag = cipher.getAuthTag();
217
+
218
+ return JSON.stringify({
219
+ salt: salt.toString('hex'),
220
+ iv: iv.toString('hex'),
221
+ authTag: authTag.toString('hex'),
222
+ encrypted,
223
+ });
224
+ }
225
+ ```
226
+
227
+ ### 3. Security Headers
228
+
229
+ ```typescript
230
+ import helmet from 'helmet';
231
+
232
+ // Comprehensive security headers
233
+ app.use(helmet({
234
+ contentSecurityPolicy: {
235
+ directives: {
236
+ defaultSrc: ["'self'"],
237
+ scriptSrc: [
238
+ "'self'",
239
+ "'strict-dynamic'",
240
+ (req, res) => `'nonce-${res.locals.nonce}'`,
241
+ ],
242
+ styleSrc: ["'self'", "'unsafe-inline'"], // Consider using nonces for styles too
243
+ imgSrc: ["'self'", "data:", "https:"],
244
+ fontSrc: ["'self'", "https://fonts.gstatic.com"],
245
+ connectSrc: ["'self'", "https://api.example.com"],
246
+ frameSrc: ["'none'"],
247
+ objectSrc: ["'none'"],
248
+ baseUri: ["'self'"],
249
+ formAction: ["'self'"],
250
+ upgradeInsecureRequests: [],
251
+ blockAllMixedContent: [],
252
+ },
253
+ reportOnly: false,
254
+ },
255
+ crossOriginEmbedderPolicy: true,
256
+ crossOriginOpenerPolicy: { policy: 'same-origin' },
257
+ crossOriginResourcePolicy: { policy: 'same-origin' },
258
+ dnsPrefetchControl: { allow: false },
259
+ frameguard: { action: 'deny' },
260
+ hsts: {
261
+ maxAge: 31536000,
262
+ includeSubDomains: true,
263
+ preload: true,
264
+ },
265
+ ieNoOpen: true,
266
+ noSniff: true,
267
+ originAgentCluster: true,
268
+ permittedCrossDomainPolicies: { permittedPolicies: 'none' },
269
+ referrerPolicy: { policy: 'strict-origin-when-cross-origin' },
270
+ xssFilter: true,
271
+ }));
272
+
273
+ // CSP nonce generation
274
+ app.use((req, res, next) => {
275
+ res.locals.nonce = crypto.randomBytes(16).toString('base64');
276
+ next();
277
+ });
278
+
279
+ // Custom security headers
280
+ app.use((req, res, next) => {
281
+ // Prevent caching of sensitive responses
282
+ if (req.path.startsWith('/api/')) {
283
+ res.set('Cache-Control', 'no-store, no-cache, must-revalidate, private');
284
+ res.set('Pragma', 'no-cache');
285
+ res.set('Expires', '0');
286
+ }
287
+
288
+ // Feature policy / Permissions policy
289
+ res.set('Permissions-Policy',
290
+ 'accelerometer=(), camera=(), geolocation=(), gyroscope=(), ' +
291
+ 'magnetometer=(), microphone=(), payment=(), usb=()'
292
+ );
293
+
294
+ // Clear site data on logout
295
+ if (req.path === '/logout') {
296
+ res.set('Clear-Site-Data', '"cache", "cookies", "storage"');
297
+ }
298
+
299
+ next();
300
+ });
301
+
302
+ // CSP violation reporting
303
+ app.post('/csp-report', express.json({ type: 'application/csp-report' }), (req, res) => {
304
+ const report = req.body['csp-report'];
305
+
306
+ logger.warn({
307
+ type: 'csp_violation',
308
+ violatedDirective: report['violated-directive'],
309
+ blockedUri: report['blocked-uri'],
310
+ documentUri: report['document-uri'],
311
+ sourceFile: report['source-file'],
312
+ lineNumber: report['line-number'],
313
+ });
314
+
315
+ res.status(204).end();
316
+ });
317
+ ```
318
+
319
+ ### 4. Input Validation & Sanitization
320
+
321
+ ```typescript
322
+ import { z } from 'zod';
323
+ import DOMPurify from 'isomorphic-dompurify';
324
+ import sqlstring from 'sqlstring';
325
+
326
+ // Strict input validation schemas
327
+ const UserInputSchema = z.object({
328
+ email: z.string().email().max(255).toLowerCase(),
329
+ name: z.string()
330
+ .min(2)
331
+ .max(100)
332
+ .regex(/^[a-zA-Z\s'-]+$/, 'Invalid characters in name'),
333
+ phone: z.string()
334
+ .regex(/^\+?[1-9]\d{1,14}$/, 'Invalid phone number')
335
+ .optional(),
336
+ bio: z.string().max(1000).optional(),
337
+ });
338
+
339
+ // HTML sanitization for rich text
340
+ function sanitizeHTML(html: string): string {
341
+ return DOMPurify.sanitize(html, {
342
+ ALLOWED_TAGS: ['b', 'i', 'em', 'strong', 'a', 'p', 'br', 'ul', 'ol', 'li'],
343
+ ALLOWED_ATTR: ['href', 'target', 'rel'],
344
+ ALLOW_DATA_ATTR: false,
345
+ });
346
+ }
347
+
348
+ // SQL injection prevention (for raw queries)
349
+ function sanitizeSQL(input: string): string {
350
+ return sqlstring.escape(input);
351
+ }
352
+
353
+ // Path traversal prevention
354
+ function sanitizePath(userPath: string, basePath: string): string {
355
+ const resolvedPath = path.resolve(basePath, userPath);
356
+
357
+ if (!resolvedPath.startsWith(path.resolve(basePath))) {
358
+ throw new Error('Path traversal detected');
359
+ }
360
+
361
+ return resolvedPath;
362
+ }
363
+
364
+ // File upload validation
365
+ const ALLOWED_MIME_TYPES = ['image/jpeg', 'image/png', 'image/gif', 'application/pdf'];
366
+ const MAX_FILE_SIZE = 10 * 1024 * 1024; // 10MB
367
+
368
+ async function validateFileUpload(file: Express.Multer.File): Promise<void> {
369
+ // Check file size
370
+ if (file.size > MAX_FILE_SIZE) {
371
+ throw new Error('File too large');
372
+ }
373
+
374
+ // Verify MIME type using magic bytes
375
+ const fileType = await import('file-type');
376
+ const type = await fileType.fromBuffer(file.buffer);
377
+
378
+ if (!type || !ALLOWED_MIME_TYPES.includes(type.mime)) {
379
+ throw new Error('Invalid file type');
380
+ }
381
+
382
+ // Check for malicious content in images
383
+ if (type.mime.startsWith('image/')) {
384
+ await scanImageForMalware(file.buffer);
385
+ }
386
+ }
387
+ ```
388
+
389
+ ### 5. Audit Logging
390
+
391
+ ```typescript
392
+ interface AuditEvent {
393
+ timestamp: Date;
394
+ eventType: string;
395
+ userId?: string;
396
+ resourceType?: string;
397
+ resourceId?: string;
398
+ action: string;
399
+ outcome: 'success' | 'failure';
400
+ ipAddress: string;
401
+ userAgent?: string;
402
+ details?: Record<string, any>;
403
+ requestId?: string;
404
+ }
405
+
406
+ class AuditLogger {
407
+ async log(event: AuditEvent): Promise<void> {
408
+ // Store in append-only audit log
409
+ await db.auditLog.create({
410
+ data: {
411
+ ...event,
412
+ timestamp: event.timestamp || new Date(),
413
+ hash: this.calculateHash(event), // Tamper detection
414
+ },
415
+ });
416
+
417
+ // Send to SIEM for real-time analysis
418
+ await this.sendToSIEM(event);
419
+ }
420
+
421
+ private calculateHash(event: AuditEvent): string {
422
+ const content = JSON.stringify({
423
+ ...event,
424
+ timestamp: event.timestamp.toISOString(),
425
+ });
426
+
427
+ return crypto
428
+ .createHmac('sha256', process.env.AUDIT_SECRET!)
429
+ .update(content)
430
+ .digest('hex');
431
+ }
432
+
433
+ private async sendToSIEM(event: AuditEvent): Promise<void> {
434
+ // Send to security information and event management system
435
+ await fetch(process.env.SIEM_ENDPOINT!, {
436
+ method: 'POST',
437
+ headers: { 'Content-Type': 'application/json' },
438
+ body: JSON.stringify(event),
439
+ });
440
+ }
441
+ }
442
+
443
+ // Audit middleware
444
+ function auditMiddleware(action: string, resourceType: string) {
445
+ return async (req: Request, res: Response, next: NextFunction) => {
446
+ const startTime = Date.now();
447
+
448
+ res.on('finish', async () => {
449
+ await auditLogger.log({
450
+ timestamp: new Date(),
451
+ eventType: 'api_call',
452
+ userId: req.user?.id,
453
+ resourceType,
454
+ resourceId: req.params.id,
455
+ action,
456
+ outcome: res.statusCode < 400 ? 'success' : 'failure',
457
+ ipAddress: req.ip,
458
+ userAgent: req.headers['user-agent'],
459
+ requestId: req.headers['x-request-id'] as string,
460
+ details: {
461
+ method: req.method,
462
+ path: req.path,
463
+ statusCode: res.statusCode,
464
+ duration: Date.now() - startTime,
465
+ },
466
+ });
467
+ });
468
+
469
+ next();
470
+ };
471
+ }
472
+
473
+ // Security-sensitive actions require audit
474
+ app.delete('/api/users/:id',
475
+ auditMiddleware('delete', 'user'),
476
+ deleteUser
477
+ );
478
+
479
+ app.post('/api/admin/roles',
480
+ auditMiddleware('create', 'role'),
481
+ createRole
482
+ );
483
+ ```
484
+
485
+ ### 6. Compliance Frameworks
486
+
487
+ ```typescript
488
+ // GDPR compliance helpers
489
+ class GDPRCompliance {
490
+ // Right to access - export user data
491
+ async exportUserData(userId: string): Promise<UserDataExport> {
492
+ const user = await db.user.findUnique({
493
+ where: { id: userId },
494
+ include: {
495
+ orders: true,
496
+ addresses: true,
497
+ preferences: true,
498
+ activityLog: true,
499
+ },
500
+ });
501
+
502
+ return {
503
+ personalData: {
504
+ name: user.name,
505
+ email: user.email,
506
+ phone: user.phone,
507
+ createdAt: user.createdAt,
508
+ },
509
+ orders: user.orders,
510
+ addresses: user.addresses,
511
+ preferences: user.preferences,
512
+ activityLog: user.activityLog,
513
+ exportedAt: new Date(),
514
+ };
515
+ }
516
+
517
+ // Right to erasure - delete user data
518
+ async eraseUserData(userId: string): Promise<void> {
519
+ await db.$transaction([
520
+ db.activityLog.deleteMany({ where: { userId } }),
521
+ db.address.deleteMany({ where: { userId } }),
522
+ db.preference.deleteMany({ where: { userId } }),
523
+ // Anonymize orders (keep for accounting)
524
+ db.order.updateMany({
525
+ where: { userId },
526
+ data: { userId: null, customerName: 'DELETED' },
527
+ }),
528
+ db.user.delete({ where: { id: userId } }),
529
+ ]);
530
+
531
+ await auditLogger.log({
532
+ timestamp: new Date(),
533
+ eventType: 'gdpr_erasure',
534
+ userId,
535
+ action: 'data_erasure',
536
+ outcome: 'success',
537
+ });
538
+ }
539
+
540
+ // Data retention enforcement
541
+ async enforceRetention(): Promise<void> {
542
+ const retentionPolicies = [
543
+ { table: 'activityLog', retentionDays: 90 },
544
+ { table: 'sessions', retentionDays: 30 },
545
+ { table: 'auditLog', retentionDays: 365 * 7 }, // 7 years for compliance
546
+ ];
547
+
548
+ for (const policy of retentionPolicies) {
549
+ const cutoff = new Date();
550
+ cutoff.setDate(cutoff.getDate() - policy.retentionDays);
551
+
552
+ await db[policy.table].deleteMany({
553
+ where: { createdAt: { lt: cutoff } },
554
+ });
555
+ }
556
+ }
557
+ }
558
+
559
+ // PCI-DSS compliance
560
+ const pciCompliance = {
561
+ // Never store CVV
562
+ sanitizePaymentData(data: PaymentData): SanitizedPaymentData {
563
+ return {
564
+ cardLastFour: data.cardNumber.slice(-4),
565
+ cardBrand: detectCardBrand(data.cardNumber),
566
+ expiryMonth: data.expiryMonth,
567
+ expiryYear: data.expiryYear,
568
+ // CVV is NEVER stored
569
+ };
570
+ },
571
+
572
+ // Mask PAN in logs
573
+ maskPAN(pan: string): string {
574
+ return pan.slice(0, 6) + '******' + pan.slice(-4);
575
+ },
576
+ };
577
+ ```
578
+
579
+ ## Use Cases
580
+
581
+ ### 1. API Security Hardening
582
+
583
+ ```typescript
584
+ // Complete API security setup
585
+ app.use(helmet());
586
+ app.use(rateLimiter);
587
+ app.use(verifyIdentity);
588
+ app.use(auditMiddleware);
589
+ ```
590
+
591
+ ### 2. Secure File Handling
592
+
593
+ ```typescript
594
+ // Secure file upload endpoint
595
+ app.post('/upload', authenticate, async (req, res) => {
596
+ await validateFileUpload(req.file);
597
+ const safePath = sanitizePath(req.body.path, UPLOAD_DIR);
598
+ // ... process file
599
+ });
600
+ ```
601
+
602
+ ## Best Practices
603
+
604
+ ### Do's
605
+
606
+ - **Defense in depth** - Multiple layers of security
607
+ - **Principle of least privilege** - Minimal permissions
608
+ - **Regular security audits** - Penetration testing
609
+ - **Automated vulnerability scanning** - CI/CD integration
610
+ - **Incident response planning** - Document procedures
611
+ - **Security training** - Educate team members
612
+
613
+ ### Don'ts
614
+
615
+ - Don't store secrets in code
616
+ - Don't trust client input
617
+ - Don't expose stack traces
618
+ - Don't use deprecated crypto
619
+ - Don't skip security headers
620
+ - Don't ignore security alerts
621
+
622
+ ## Related Skills
623
+
624
+ - **owasp** - Security fundamentals
625
+ - **oauth** - Authentication patterns
626
+ - **defense-in-depth** - Layered security
627
+
628
+ ## Reference Resources
629
+
630
+ - [OWASP Cheat Sheets](https://cheatsheetseries.owasp.org/)
631
+ - [HashiCorp Vault](https://www.vaultproject.io/docs)
632
+ - [Content Security Policy](https://developer.mozilla.org/en-US/docs/Web/HTTP/CSP)
633
+ - [SOC 2 Compliance](https://www.aicpa.org/soc2)