Skip to main content

Free 30-min security demo  โ€” We'll scan your real code and show live findings, no commitment Book Now

Offensive360
Home / Knowledge Base / Sensitive Data Exposure in Logs
Medium CWE-532 A09:2021 Security Logging and Monitoring Failures

Sensitive Data Exposure in Logs

Logging sensitive data such as passwords, tokens, PII, and credit card numbers creates security and compliance risks when logs are stored, transmitted, or accessed by unauthorized parties.

Affects: C#JavaPythonJavaScriptPHPRubyGo

What is Sensitive Data Exposure in Logs?

Sensitive data in logs occurs when an application writes security-critical or privacy-sensitive information to log files, including: passwords, authentication tokens (JWT, API keys, session IDs), credit card or bank account numbers, personally identifiable information (PII), health information (PHI), and encryption keys.

Logs are typically retained for extended periods, replicated to SIEM systems, backed up to less-secure storage, and accessed by a wider audience than production databases. Data that is carefully protected in a database may be freely readable in log files. Compliance frameworks (PCI-DSS, HIPAA, GDPR) explicitly prohibit logging certain categories of data.

How this occurs

Sensitive data enters logs via multiple paths:

  1. Debugging code left in production โ€” log.Debug("User password: " + password)
  2. Logging entire request/response bodies โ€” Middleware that logs HTTP payloads containing form fields or JSON with passwords
  3. Exception messages โ€” Stack traces that include method arguments containing sensitive values
  4. ORM/database logging โ€” Query loggers that record parameterized values alongside SQL statements

Vulnerable code examples

Java โ€” direct password logging

// VULNERABLE: Password written to log
public void authenticate(String username, String password) {
    log.debug("Authenticating user: {} with password: {}", username, password);
    // ...
}

C# โ€” full request body logging

// VULNERABLE: HTTP middleware logging entire request body โ€” may include passwords, tokens
app.Use(async (context, next) => {
    context.Request.EnableBuffering();
    var body = await new StreamReader(context.Request.Body).ReadToEndAsync();
    _logger.LogDebug("Request body: {Body}", body); // Logs passwords from login forms
    context.Request.Body.Position = 0;
    await next();
});

Node.js โ€” JWT token in log

// VULNERABLE: Full Authorization header (bearing the JWT) logged
app.use((req, res, next) => {
    console.log(`${req.method} ${req.path} - Auth: ${req.headers.authorization}`);
    next();
});

Secure code examples

Java โ€” log username only, never password

// SECURE: Log only non-sensitive fields; omit credentials entirely
public void authenticate(String username, String password) {
    log.debug("Authentication attempt for username: {}", username);
    // password is never referenced in any log statement
}

C# โ€” selective request logging with field masking

// SECURE: Log only safe request metadata; mask or exclude sensitive fields
app.Use(async (context, next) => {
    _logger.LogInformation("Request: {Method} {Path} from {IP}",
        context.Request.Method,
        context.Request.Path,
        context.Connection.RemoteIpAddress);
    // Body NOT logged โ€” or if needed, parse and redact sensitive fields first
    await next();
});

Python / Django โ€” structured logging with field exclusion

import logging
import re

logger = logging.getLogger(__name__)

SENSITIVE_FIELDS = {'password', 'token', 'secret', 'api_key', 'credit_card', 'ssn'}

def safe_log_dict(data: dict) -> dict:
    """Return a copy of dict with sensitive values masked."""
    return {
        k: '***REDACTED***' if k.lower() in SENSITIVE_FIELDS else v
        for k, v in data.items()
    }

def login_view(request):
    data = request.POST.dict()
    logger.info("Login attempt: %s", safe_log_dict(data))  # password โ†’ ***REDACTED***

What Offensive360 detects

  • Password/secret in log calls โ€” Log statements where the argument is a variable named password, secret, token, apiKey, credential, etc.
  • Full request body logging โ€” Middleware or interceptors that log HTTP request/response bodies without field filtering
  • Exception logging with sensitive arguments โ€” log.error(e) where exception messages may contain parameter values
  • SQL query logging with values โ€” ORM or JDBC logging configurations that record query parameters

Remediation guidance

  1. Never log passwords or secrets โ€” Under any circumstances, at any log level. Remove all such statements from both production and debug paths.

  2. Mask sensitive fields in structured logs โ€” When logging request/response data, parse the payload and replace sensitive field values with [REDACTED] before writing.

  3. Avoid logging full request bodies โ€” If request logging is required for debugging, log only metadata (method, path, status, timing) and exclude body content.

  4. Disable verbose ORM/query logging in production โ€” Hibernate, Entity Framework, and SQLAlchemy query loggers can expose parameter values. Restrict to development environments only.

  5. Audit log retention and access โ€” Ensure log files are stored with appropriate access controls, encrypted at rest, and retained only as long as required by policy.

References

By Offensive360 Security Research Reviewed: March 2026

Detect Sensitive Data Exposure in Logs automatically

Run Offensive360 SAST on your codebase to find this and 100+ other vulnerabilities.