Skip to main content

Overview

EverShop provides a centralized logging system built on Winston. The logger supports multiple log levels, custom formatting with colors and icons, and flexible output destinations (console or file).

Logger Functions

debug()

Log debug-level messages.
import { debug } from '@evershop/evershop/src/lib/log/logger';

debug('Processing order #123');
debug({ orderId: 123, status: 'processing' });
Location: packages/evershop/src/lib/log/logger.js:14
Debug logs are only output in development mode or when the --debug flag is passed.

info()

Log informational messages.
import { info } from '@evershop/evershop/src/lib/log/logger';

info('Server started on port 3000');
info('Database connection established');
Location: packages/evershop/src/lib/log/logger.js:29

success()

Log success messages (alias for info).
import { success } from '@evershop/evershop/src/lib/log/logger';

success('Order created successfully');
success('Payment processed');
Location: packages/evershop/src/lib/log/logger.js:34

warning()

Log warning messages.
import { warning } from '@evershop/evershop/src/lib/log/logger';

warning('Product stock is running low');
warning('Cache miss for product ID 123');
Location: packages/evershop/src/lib/log/logger.js:23

error()

Log error messages with stack traces.
import { error } from '@evershop/evershop/src/lib/log/logger';

try {
  await processOrder();
} catch (err) {
  error(err);
  // Stack trace is automatically included
}

// Or log error messages directly
error('Failed to connect to database');
Location: packages/evershop/src/lib/log/logger.js:19

Log Levels

Winston log levels supported (in order of priority):
error
level 0
Critical errors that require immediate attentionIcon: ❌ | Color: Red
warn
level 1
Warning messages for potentially problematic situationsIcon: ⚠️ | Color: Yellow
info
level 2
Informational messages about normal operationIcon: ℹ️ | Color: Green
http
level 3
HTTP request/response loggingIcon: 🌐 | Color: Blue
verbose
level 4
Verbose diagnostic informationIcon: 🔍 | Color: Cyan
debug
level 5
Detailed debugging informationIcon: 🐛 | Color: Magenta
silly
level 6
Most detailed logging levelIcon: 🤪 | Color: Gray

Configuration

Environment Variables

Configure logging behavior with environment variables:
# Set log level (default: 'warn' in production, 'silly' in development)
LOGGER_LEVEL=info

# Log to file instead of console (production)
LOG_FILE=/var/log/evershop/app.log

# Enable debug mode
NODE_ENV=development

Log Format

Logs are formatted with:
  • Icon based on log level
  • Colored level indicator
  • Message content
  • Stack trace (for errors)
Example output:
🐛 debug: 
Processing order #123

ℹ️ info: 
Server started on port 3000

⚠️  warn: 
Product stock is running low

❌ error: 
Failed to connect to database
Error: Connection refused
    at Connection.connect (/app/db.js:45:12)
    ...
Implementation: packages/evershop/src/lib/log/logger.js:63

Logger Configuration

The logger is configured through the registry system:
import winston from 'winston';
import { addProcessor } from '@evershop/evershop/src/lib/util/registry';

addProcessor(
  'logger_configuration',
  () => {
    return {
      level: 'debug',
      format: winston.format.combine(
        winston.format.errors({ stack: true }),
        winston.format.colorize(),
        winston.format.printf(({ level, message, stack }) => {
          return `${level}: ${stack || message}`;
        })
      ),
      transports: [
        new winston.transports.Console()
      ]
    };
  },
  0  // Priority
);
Location: packages/evershop/src/lib/log/logger.js:39

Custom Colorization

EverShop uses a custom colorization formatter: Location: packages/evershop/src/lib/log/CustomColorize.js
import CustomColorize from './CustomColorize.js';

const format = winston.format.combine(
  CustomColorize({
    colors: {
      error: 'red',
      warn: 'yellow',
      info: 'green',
      debug: 'magenta'
    },
    level: false,  // Don't colorize level text
    message: true  // Colorize message content
  })
);
Usage: packages/evershop/src/lib/log/logger.js:50

Output Destinations

Console (Development)

In development mode, logs are output to the console:
transports: [new winston.transports.Console()]

File (Production)

In production, logs can be written to a file:
LOG_FILE=/var/log/evershop/app.log
transports: [
  new winston.transports.File({ filename: '/var/log/evershop/app.log' })
]
Implementation: packages/evershop/src/lib/log/logger.js:138

Exception Handling

The logger automatically captures unhandled exceptions:
exceptionHandlers: [
  new winston.transports.Console()
  // or
  new winston.transports.File({ filename: '/var/log/evershop/app.log' })
]
Location: packages/evershop/src/lib/log/logger.js:141

Best Practices

1

Use Appropriate Log Levels

  • error() for failures that need immediate attention
  • warning() for recoverable issues
  • info() for important state changes
  • debug() for detailed troubleshooting
2

Include Context

Log relevant context like IDs, user info, or operation details:
debug(`Processing order ${orderId} for customer ${customerId}`);
3

Don't Log Sensitive Data

Never log passwords, tokens, credit card numbers, or personal data:
// ✗ Bad
debug({ password: user.password });

// ✓ Good
debug({ userId: user.id, email: user.email });
4

Use Structured Logging

Log objects for better parsing and filtering:
info({
  event: 'order_created',
  orderId: 123,
  total: 99.99,
  timestamp: new Date()
});
5

Catch and Log Errors

Always catch errors and log them with context:
try {
  await processPayment(orderId);
} catch (err) {
  error(`Payment failed for order ${orderId}:`);
  error(err);
  throw err;
}

Development vs Production

Development Mode

  • Log level: silly (all logs)
  • Output: Console with colors and icons
  • Debug logs enabled
  • Stack traces shown

Production Mode

  • Log level: warn (configurable via LOGGER_LEVEL)
  • Output: File (via LOG_FILE) or console
  • Debug logs disabled (unless --debug flag)
  • Stack traces for errors only
Mode Detection: packages/evershop/src/lib/log/logger.js:9
const isDebugging = isDevelopmentMode() || process.argv.includes('--debug');

Example: Logging in a Service

import { info, error, warning, debug } from '@evershop/evershop/src/lib/log/logger';
import { select } from '@evershop/postgres-query-builder';
import { pool } from '@evershop/evershop/src/lib/postgres/connection';

export async function processOrder(orderId) {
  debug(`Starting order processing for order ${orderId}`);
  
  try {
    // Load order
    const order = await select()
      .from('order')
      .where('order_id', '=', orderId)
      .load(pool);
    
    if (!order) {
      warning(`Order ${orderId} not found`);
      return null;
    }
    
    debug(`Order ${orderId} loaded:`, order);
    
    // Process payment
    await processPayment(order);
    info(`Payment processed successfully for order ${orderId}`);
    
    // Update status
    await updateOrderStatus(orderId, 'completed');
    info(`Order ${orderId} marked as completed`);
    
    return order;
  } catch (err) {
    error(`Failed to process order ${orderId}:`);
    error(err);
    throw err;
  }
}

Build docs developers (and LLMs) love