npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

infront-logger

v1.1.19

Published

The logger supports both writing to file and to console.

Readme

Infront Logger

Logging done right

The logger supports both writing to file and to console.

npm i @infront/logger

Usage

BaseLogger

const {BaseLogger} = require('infront-logger');  
let options = {};
let logger = new BaseLogger("component1", options);  
logger.log("this is a test message");

StaticLogger

const {staticLogger} = require('infront-logger');

// Simple logging
staticLogger.info("User logged in");

// Logging with context
staticLogger.info("User action", { userId: 123, action: "login" });

// Different log levels
staticLogger.debug("Debug information");
staticLogger.info("Information message");
staticLogger.warn("Warning message");
staticLogger.error("Error occurred", { error: "Details here" });

HTTP Transport

Enable HTTP transport to send logs to a remote HTTP endpoint:

const {BaseLogger} = require('infront-logger');

// Basic HTTP transport configuration
const logger = new BaseLogger("myComponent", {
  http: {
    host: "logs.example.com",
    path: "/api/logs"
  }
});

// HTTP transport with custom headers
const logger = new BaseLogger("myComponent", {
  http: {
    host: "logs.example.com",
    path: "/api/logs",
    headers: {
      "Authorization": "Bearer token123",
      "X-API-Key": "key456"
    }
  }
});

// HTTP transport with batching enabled
const logger = new BaseLogger("myComponent", {
  http: {
    host: "logs.example.com",
    path: "/api/logs",
    batch: true,
    batchInterval: 2000  // Batch logs every 2 seconds
  }
});

// HTTP transport with common keys added to all payloads
const logger = new BaseLogger("myComponent", {
  http: {
    host: "logs.example.com",
    path: "/api/logs",
    commonKeys: {
      applicationName: "stream-engine",
      environment: "production"
    }
  }
});

logger.info("This log will be sent to the HTTP endpoint");

HttpLogger (Express Logger)

const {HttpLogger} = require('infront-logger');

const responseInterceptor = (req, res, next) => {
// Save the original response method

const originalSend = res.send;
const originalJSON = res.json;
const originalSendStatus = res.sendStatus;

let responseSent = false;
let startTime = Date.now();

// Override the response method
res.sendStatus = function(status){
try{
    const httpLogger = new HttpLogger();
    if (!responseSent) {
        res.statusCode = status;
        httpLogger.request(req);
        httpLogger.response(res);


        if (status < 400) {
          httpLogger.success();
        } else {
          httpLogger.error("req.sendStatus with error status");
        }
        responseSent = true;
      }
    } catch (err){
      console.error(err);

    }
    return originalSendStatus.call(this, status);
};

res.send = function (body){
try{
const httpLogger = new HttpLogger();
if (!responseSent) {
httpLogger.request(req);
httpLogger.response(res);
httpLogger.body(body);
        if (res.statusCode < 400) {
          httpLogger.success();
        } else {
          httpLogger.error(body.message);
        }
        responseSent = true;
      }
    } catch (err){
      console.error(err);
    }

    // Call the original response method
    return originalSend.call(this, body);
};


res.json = function (body){
try{
const httpLogger = new HttpLogger();
if (!responseSent) {
httpLogger.request(req).response(res).body(body);

        if (res.statusCode < 400) {
          httpLogger.success();
        } else {
          httpLogger.error(body.message);
        }
        responseSent = true;
      }


    } catch (err){
      console.error(err);
    }

    // Call the original response method
    return originalJSON.call(this, body);
};

// Continue processing the request
next();
}

app.use(responseInterceptor);

DatadogLogger

import {DatadogLogger} from 'infront-logger/browser';
let loggerOptions = {
    clientToken: 'YOUR_DATADOG_CLIENT_TOKEN',
    service : "SERVICE_NAME"
}	
let logger = new DatadogLogger(loggerOptions);
logger.log("this is a test message", {prop1: "val1"});

FastifyLogger

MongooseLoggerPlugin

Make sure to use before defining schemas;

const {MongooseLoggerPlugin} = require('infront-logger');
const mongoose = require('mongoose');
let plugin = MongooseLoggerPlugin({
  console: false, 
  filename: 'db.log',
  sampleRate: 0.1,  // Sample 10% of DB queries
  throttleMs: 1000  // Throttle duplicate queries to once per second
});
mongoose.plugin(plugin);

Loggers

BaseLogger

Methods

  • session(id)
  • log(msg)
  • info(msg)
  • warn(msg)
  • error(err)
  • debug(msg)
  • profile(action, options)
  • profileMem(options)
  • exclude(pattern) - Exclude messages matching string or regex pattern

StaticLogger (extends BaseLogger)

Methods

  • log(msg, context?) - Logs at info level
  • info(msg, context?)
  • warn(msg, context?)
  • error(msg, context?)
  • debug(msg, context?)

All methods support both string messages and context objects. Context objects are automatically merged into the log context.

HttpLogger (extends BaseLogger)

Methods

  • request(req)
  • response(res)
  • body(data)
  • success(req, res, body)
  • error(err)

Options

  • maxBodyLength - -1 = unlimited, default: 128

FastifyLogger (extends BaseLogger)

Methods

  • request(req)
  • response(res)
  • body(data)
  • success(req, res, body)
  • error(err)

Options

  • maxBodyLength - -1 = unlimited, default: 128

Options

  • dirname - The directory in which the logs will be created (default: "logs")
  • levels - An object of "level name : hierarchical value"
  • level - default level (default: info)
  • dateFormat : default "YYYY-MM-DD HH:mm:ss:ms"
  • file - boolean - should log to file (default : true)
  • maxFileSize: The maximum file size for a rotating file strategy (default: "30m")
  • maxFiles: The maximum number of files for a rotating file strategy (default: 2)
  • filename - name of the default log file (default: "logs.log")
  • errorFilename - name of the default error log file (default: "error.log")
  • console - boolean - should log to console (default: true)
  • consoleJSON - boolean - print full json to console (default : false)
  • http - object - Enable HTTP transport to send logs to an HTTP endpoint
    • http.host - string (required) - The HTTP endpoint host (e.g., "logs.example.com")
    • http.path - string (required) - The HTTP endpoint path (e.g., "/api/logs")
    • http.headers - object (optional) - Custom headers to include in HTTP requests (default: {})
    • http.batch - boolean (optional) - Enable batching of log messages (default: false)
    • http.batchInterval - number (optional) - Interval in milliseconds for batching logs when batch is enabled (default: 1000)
    • http.commonKeys - object (optional) - Common fields to add to all log payloads sent via HTTP transport (default: undefined)
    • Note: HTTP transport always uses SSL/HTTPS (ssl: true)
  • sampleRate - number (0.0 to 1.0) - Percentage of logs to sample. 1.0 = log everything, 0.5 = log 50%, etc. Applies to all enabled transports (console and/or file) (default: 1.0)
  • bypassSamplingForErrors - boolean - If true, error logs bypass sampling and are always logged regardless of sampleRate settings (default: true)
  • throttleMs - number - Throttle logs by milliseconds. Prevents the same log message from being logged more than once within the specified time window. 0 = no throttling (default: 0)

Advanced Features

Log Sampling

Control the volume of logs by using sampling rates. This is useful in high-traffic scenarios where you want to reduce log volume while maintaining visibility.

// Sample 50% of logs
const logger = new BaseLogger("myComponent", {
  sampleRate: 0.5  // 50% of logs will be written
});

// Sample 10% of logs
const logger = new BaseLogger("myComponent", {
  sampleRate: 0.1  // 10% of logs will be written
});

Note: The sample rate applies to all enabled transports (console and/or file). When both console and file are enabled, Winston logs to all enabled transports in a single call, so the same sample rate applies to both.

Error Log Bypass

By default, error logs bypass sampling to ensure critical errors are always logged. You can disable this behavior:

// Errors will also be subject to sampling
const logger = new BaseLogger("myComponent", {
  sampleRate: 0.1,
  bypassSamplingForErrors: false  // Errors will also be sampled
});

Log Throttling

Throttle prevents duplicate log messages from flooding your logs. The same message (same level + same content) can only be logged once within the throttle window.

// Throttle logs to once per 5 seconds
const logger = new BaseLogger("myComponent", {
  throttleMs: 5000  // Same message can only log once every 5 seconds
});

// Throttle to once per minute
const logger = new BaseLogger("myComponent", {
  throttleMs: 60000  // Same message can only log once per minute
});

How it works:

  • First occurrence of a message is always logged
  • Subsequent identical messages within the throttle window are suppressed
  • After the throttle window expires, the message can be logged again
  • The throttle cache is automatically cleaned up to prevent memory leaks

Combining Features

You can combine sampling, throttling, and error bypass:

const logger = new BaseLogger("myComponent", {
  sampleRate: 0.1,                // 10% sampling
  bypassSamplingForErrors: true,  // Always log errors (default)
  throttleMs: 5000                // Throttle duplicate messages to once per 5 seconds
});