- β Information Disclosure (HIGH) - Sanitized errors, removed stack traces
- β Sensitive Data Exposure (HIGH) - Masked emails/phones automatically
- β CORS Misconfiguration (MEDIUM) - Restricted to trusted origins
- β Missing Security Headers (LOW) - Added CSP, X-Frame-Options, etc.
// Emails: john.doe@example.com β j***e@e***e.com
// Phones: +6281234567890 β +62812****7890
// Tokens: secrettoken123 β s***3// Production: "Terjadi kesalahan. Silakan coba lagi."
// Development: Full error details for debugging
// NEVER: Stack traces, API keys, database structure// β
Allowed: https://travo-mate.vercel.app
// β
Allowed: http://localhost:8080 (dev only)
// β Blocked: All other originsX-Frame-Options: DENY
X-Content-Type-Options: nosniff
X-XSS-Protection: 1; mode=block
Content-Security-Policy: (strict)
import { maskEmail, maskPhoneNumber } from '@/utils/dataMasking';
<p>Email: {maskEmail(user.email)}</p>
<p>Phone: {maskPhoneNumber(booking.phone)}</p>import { getUserFriendlyError, logError } from '@/utils/errorSanitization';
try {
await operation();
} catch (error) {
toast.error(getUserFriendlyError(error)); // Indonesian message
logError('Context', error); // Dev only
}import { getUserBookingsWithMasking } from '@/utils/supabaseHelpers';
// Auto-masks for non-admin users
const bookings = await getUserBookingsWithMasking(userId, !isAdmin);# Vercel Environment Variables
APP_URL=https://travo-mate.vercel.app # For CORS
NODE_ENV=production # Enables securityEdit api/midtrans.ts and api/gemini.ts:
const allowedOrigins = [
'https://travo-mate.vercel.app',
'https://your-custom-domain.com', // Add your domain here
];curl -I https://travo-mate.vercel.app// Browser console
import { maskEmail } from '@/utils/dataMasking';
maskEmail('test@example.com'); // β t***t@e***e.com# Should FAIL
curl -H "Origin: https://evil.com" https://travo-mate.vercel.app/api/midtrans
# Should SUCCEED
curl -H "Origin: https://travo-mate.vercel.app" https://travo-mate.vercel.app/api/midtrans- All secrets use correct env var naming (no VITE_ for server keys)
- CORS allowedOrigins includes production domain
- Security headers configured in vercel.json
- Data masking applied to user-facing components
- Error messages use getUserFriendlyError()
- Console.log wrapped with logError() or NODE_ENV check
- Test locally:
bun run dev - Build succeeds:
bun run build - Deploy to Vercel
- Run security scan to verify
| Issue | Solution |
|---|---|
| CORS errors | Check APP_URL in Vercel env vars |
| Data not masked | Verify isAdmin() function works |
| Errors still show stack traces | Check NODE_ENV=production |
| CSP violations | Add domain to vercel.json CSP |
- Complete Guide:
docs/SECURITY_FIXES_2025-11-03.md - Code Examples:
docs/SECURITY_USAGE_EXAMPLES.md - AI Instructions:
.github/copilot-instructions.md
Last Updated: November 3, 2025
Status: Production Ready β