MEDIUM log injectionexpressfirestore

Log Injection in Express with Firestore

Log Injection in Express with Firestore — how this specific combination creates or exposes the vulnerability

Log injection occurs when untrusted input is written directly into log entries without validation or sanitization, allowing an attacker to inject additional log lines or forge log metadata. In an Express application using Firestore as the backend data store, this risk arises at the intersection of HTTP request handling and Firestore write operations.

Express request and response objects often contain user-controlled data such as query parameters, headers, and body fields. If this data is passed directly into Firestore document writes or used to construct log messages, newline characters (e.g., \n and \r) can alter the structure of log output. For example, an attacker could supply a display name or comment field containing malicious newline and text sequences, causing a single logical log entry to become multiple entries or to inject fake log lines that appear authoritative.

Consider a typical write to Firestore triggered by an Express route:

const express = require('express');
const { initializeApp } = require('firebase-admin');
const app = express();
app.use(express.json());

app.post('/comment', async (req, res) => {
  const { text, userId } = req.body;
  // Risky: directly using user input in a Firestore document
  await initializeApp().firestore().collection('comments').add({
    text,
    userId,
    createdAt: new Date(),
  });
  res.sendStatus(200);
});

If the text field contains newline characters, and the application or infrastructure logs Firestore operations (e.g., via Cloud Logging or custom middleware), the injected newlines can create fabricated log lines that misrepresent the sequence of events. This can obscure the true origin of actions or make it harder to correlate logs during incident investigations.

Additionally, if the Express app logs request details before writing to Firestore—such as printing the full request body or user ID—unsanitized input can directly pollute those logs. For instance, logging an object with newline-containing fields may result in multi-line entries that break log parsers or allow an attacker to simulate structured log entries. Such injected content might be misinterpreted as legitimate log metadata, leading to confusion during audits or monitoring.

The vulnerability is not in Firestore itself, but in how the Express layer handles and logs user-supplied data before it reaches Firestore. Defense requires sanitizing and validating all inputs used in both application logs and Firestore documents, and ensuring logging practices do not directly concatenate raw user data.

Firestore-Specific Remediation in Express — concrete code fixes

To mitigate log injection when using Express with Firestore, you should normalize user input before it touches logs or Firestore writes. This includes stripping or encoding newline characters and other control characters, validating field lengths and formats, and structuring log messages in a way that prevents injection.

1. Sanitize inputs before Firestore writes

Remove or replace newline and carriage return characters in user-supplied strings. This prevents injected line breaks from affecting logs or document content.

function sanitizeInput(value) {
  if (typeof value !== 'string') return value;
  return value.replace(/[\r\n]+/g, ' ').trim();
}

const express = require('express');
const { initializeApp } = require('firebase-admin');
const app = express();
app.use(express.json());

app.post('/comment', async (req, res) => {
  const rawText = req.body.text;
  const text = sanitizeInput(rawText);
  const userId = sanitizeInput(req.body.userId);

  await initializeApp().firestore().collection('comments').add({
    text,
    userId,
    createdAt: new Date(),
  });
  res.sendStatus(200);
});

2. Use structured logging with explicit fields

Instead of concatenating user data into log messages, use structured logging objects. This keeps log lines intact and prevents newline-based injection from splitting entries.

const logger = {
  info: (message, metadata) => {
    console.log(JSON.stringify({ level: 'info', message, ...metadata }));
  },
};

app.post('/comment', async (req, res) => {
  const text = sanitizeInput(req.body.text);
  logger.info('Comment created', {
    userId: sanitizeInput(req.body.userId),
    textLength: text.length,
    timestamp: new Date().toISOString(),
  });
  res.sendStatus(200);
});

3. Validate data before writing to Firestore

Enforce constraints on expected formats and lengths. Reject or transform input that does not comply, reducing the likelihood of malicious payloads reaching Firestore or logs.

function isValidComment(text) {
  return typeof text === 'string' && text.length > 0 && text.length <= 1000;
}

app.post('/comment', async (req, res) => {
  const text = sanitizeInput(req.body.text);
  if (!isValidComment(text)) {
    return res.status(400).send('Invalid comment');
  }
  await initializeApp().firestore().collection('comments').add({
    text,
    userId: sanitizeInput(req.body.userId),
    createdAt: new Date(),
  });
  res.sendStatus(200);
});

These practices help ensure that log entries remain coherent and that Firestore documents contain clean, predictable data. They also align with secure coding principles for handling external input in web applications.

Frequently Asked Questions

Can log injection affect the accuracy of compliance reports generated from Firestore logs?
Yes. If newline characters in user input corrupt log structure, compliance reports derived from those logs may misrepresent events, making it harder to demonstrate adherence to frameworks such as OWASP API Top 10 or GDPR.
Does middleBrick detect log injection risks in Express and Firestore integrations?
middleBrick scans unauthenticated attack surfaces and can surface findings related to input validation and data exposure that may indicate log injection risks. Use the middlebrick CLI or Dashboard to track these findings and map them to remediation guidance.