This document provides comprehensive guidance on using json-io securely in production environments, including security features, configuration options, and best practices.
- Security Features
- Security Configuration
- Protection Against Common Attacks
- Security Best Practices
- Security Testing
- Incident Response
- Security Updates
json-io includes comprehensive security protections implemented across all major components:
DoS Attack Prevention via Bounded Processing:
- Collection size limits (1M objects maximum)
- Stack depth limits (10K maximum depth)
- String length limits (64KB for individual strings)
- Resource file size limits (1MB maximum)
// These limits are automatically enforced - no configuration needed ReadOptions options = new ReadOptionsBuilder().build();
Safe Reflection Operations:
- SecurityManager validation for all reflection operations
- Safe setAccessible() usage with graceful fallbacks
- VarHandle/MethodHandle security with permission checks
- Protection against injection into system classes
// Reflection security is automatically enabled // For restricted environments, graceful fallbacks are used JsonIo.toJava(jsonString, readOptions);
Comprehensive Input Validation:
- Null safety checks throughout the codebase
- Array bounds validation in all array operations
- Reference ID validation against malicious attacks
- Directory traversal prevention in resource loading
Memory Leak Prevention:
- ThreadLocal cleanup to prevent memory leaks
- Proper stream closure with try-with-resources
- Cache eviction strategies for bounded memory usage
- Enhanced error handling with resource cleanup
json-io comes with secure defaults enabled out of the box:
// Default configuration includes all security protections ReadOptions secureOptions = new ReadOptionsBuilder().build(); WriteOptions secureWriteOptions = new WriteOptionsBuilder().build();
For high-security environments, you can implement additional restrictions:
// Example: Custom validation for additional security ReadOptions restrictedOptions = new ReadOptionsBuilder() .failOnUnknownType(true) // Reject unknown types .allowNanAndInfinity(false) // Reject NaN/Infinity .build();
Recommended settings for production:
ReadOptions productionOptions = new ReadOptionsBuilder() .failOnUnknownType(true) // Security: Reject unknown types .allowNanAndInfinity(false) // Security: Reject problematic numbers .build(); WriteOptions productionWriteOptions = new WriteOptionsBuilder() .writeEnumsAsJsonObjects(true) // Consistency: Structured enum handling .alwaysShowType(false) // Performance: Minimize type info .build();
Protection: Automatic depth limiting prevents stack overflow from deeply nested JSON.
// Malicious deeply nested JSON is automatically rejected: // {"nested":{"nested":{"nested":{...}}}} // 15000+ levels deep // Throws JsonIoException with "stack depth" message
Protection: Collection size limits prevent memory exhaustion.
// Large collections are automatically limited: // [item1, item2, ...] // 1M+ items // Throws JsonIoException with "Security limit exceeded" message
Protection: Class loading restrictions prevent malicious class instantiation.
// Dangerous classes are automatically blocked: // {"@type":"java.lang.Runtime", "value":"test"} // {"@type":"java.lang.ProcessBuilder", "value":"test"} // Returns null or throws security exception
Protection: Reference tracking limits prevent exponential object creation.
// Reference explosion patterns are detected and limited: // Multiple objects referencing each other exponentially // Throws JsonIoException when limits exceeded
Protection: Safe string processing handles malicious unicode.
// Malicious unicode patterns are safely processed: // Control characters, normalization attacks, homographs // Processed safely without security vulnerabilities
Always validate JSON input from untrusted sources:
public Object parseUntrustedJson(String jsonInput) { try { // Validate input size if (jsonInput.length() > MAX_JSON_SIZE) { throw new SecurityException("JSON input too large"); } // Use secure options ReadOptions secureOptions = new ReadOptionsBuilder() .failOnUnknownType(true) .build(); return JsonIo.toJava(jsonInput, secureOptions); } catch (JsonIoException e) { // Log security events logger.warn("JSON parsing failed: {}", e.getMessage()); throw new SecurityException("Invalid JSON input", e); } }
Implement secure error handling:
public Object secureJsonParsing(String json) { try { return JsonIo.toJava(json, readOptions); } catch (JsonIoException e) { // Don't expose internal details in error messages logger.error("JSON parsing error", e); throw new SecurityException("JSON parsing failed"); } }
Set appropriate resource limits for your environment:
// Monitor memory usage Runtime runtime = Runtime.getRuntime(); long maxMemory = runtime.maxMemory(); long usedMemory = runtime.totalMemory() - runtime.freeMemory(); if (usedMemory > maxMemory * 0.8) { // Implement back-pressure or reject new requests throw new SecurityException("Memory usage too high"); }
Implement comprehensive security logging:
public Object monitoredJsonParsing(String json) { long startTime = System.nanoTime(); String source = getCurrentRequestSource(); try { Object result = JsonIo.toJava(json, readOptions); // Log successful parsing with metrics long duration = System.nanoTime() - startTime; securityLogger.info("JSON parsed successfully - source: {}, duration: {}ms", source, duration / 1_000_000); return result; } catch (JsonIoException e) { // Log security events with context securityLogger.warn("JSON parsing failed - source: {}, error: {}, input_size: {}", source, e.getMessage(), json.length()); throw e; } }
Implement additional class filtering for high-security environments:
ReadOptions restrictiveOptions = new ReadOptionsBuilder() .failOnUnknownType(true) .addClassFactory(YourClass.class, new SecureClassFactory()) .build(); // Custom class factory with security validation public class SecureClassFactory implements JsonReader.ClassFactory { private static final Set<String> ALLOWED_PACKAGES = Set.of( "com.yourcompany.dto", "com.yourcompany.model" ); @Override public Object newInstance(Class<?> c, JsonObject jsonObj, Resolver resolver) { String packageName = c.getPackage().getName(); if (!ALLOWED_PACKAGES.contains(packageName)) { throw new SecurityException("Class not allowed: " + c.getName()); } return ClassUtilities.newInstance(c); } }
Use the provided security fuzz tests:
// Run comprehensive security tests mvn test -Dtest=SecurityFuzzTest
Test common attack vectors:
@Test public void testSecurityLimits() { // Test deep nesting testDeeplyNestedInput(); // Test large collections testLargeCollectionInput(); // Test malicious references testMaliciousReferenceInput(); // Test class injection testClassInjectionInput(); }
Validate that security controls don't impact performance:
// Run performance benchmarks mvn test -Dtest=PerformanceBenchmarkTest
Monitor for these security events:
- Excessive Memory Usage: Monitor heap usage during JSON processing
- Processing Time Anomalies: Detect unusually long processing times
- Security Exceptions: Track JsonIoException with security messages
- Class Loading Failures: Monitor failed class instantiation attempts
-
Immediate Response:
- Isolate the affected system
- Stop processing the malicious input
- Preserve logs for analysis
-
Analysis:
- Analyze the malicious JSON input
- Identify the attack vector used
- Assess potential data exposure
-
Remediation:
- Apply additional input validation
- Update security configurations
- Implement additional monitoring
-
Recovery:
- Restart affected services
- Verify system integrity
- Resume normal operations
- Monitor Releases: Watch the json-io GitHub repository for security updates
- Update Dependencies: Keep json-io and java-util updated to latest versions
- Security Advisories: Subscribe to security notifications
Current security-hardened version: 4.57.0 (unreleased)
Security improvements included:
- Memory exhaustion protection
- Reflection security hardening
- Input validation & bounds checking
- Resource management enhancements
- Thread safety improvements
To report security vulnerabilities:
- Do not create public GitHub issues for security problems
- Email security reports to: [security contact - update as needed]
- Include detailed reproduction steps
- Allow reasonable time for response and patching
json-io's security features help meet various compliance requirements:
- OWASP Top 10: Protection against injection and security misconfiguration
- NIST Cybersecurity Framework: Input validation and secure development practices
- ISO 27001: Information security management controls
- PCI DSS: Secure coding practices for payment card environments
Use this checklist to ensure secure json-io deployment:
- Using latest security-hardened version
- Configured with secure ReadOptions/WriteOptions
- Implemented proper input validation
- Added comprehensive error handling
- Set up security logging and monitoring
- Tested with SecurityFuzzTest suite
- Validated performance with benchmarks
- Implemented incident response procedures
- Established security update process
Remember: Security is a process, not a product. Regularly review and update your security measures as threats evolve.