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

smorg-utils

v1.0.1

Published

A lightweight, tree-shakable utility library with TypeScript support

Readme

🧰 smorg-utils

npm version TypeScript License: MIT

A lightweight, tree-shakable utility library with TypeScript support. Built with modern JavaScript standards, optimized for minimal bundle size and maximum performance.

✨ Features

  • 🌳 Tree-shakable - Import only what you need
  • 📦 Dual module support - Both ESM and CommonJS
  • 🔷 TypeScript first - Full type safety and IntelliSense
  • 🚀 Zero dependencies - No external dependencies
  • 📱 Universal - Works in Node.js and browsers
  • High performance - Optimized for speed
  • 🧪 Well tested - Comprehensive test coverage
  • 🔌 Modular - Plugin-based architecture

📦 Installation

npm install smorg-utils
yarn add smorg-utils
pnpm add smorg-utils

🚀 Quick Start

1. Basic Usage (Zero Configuration)

import { logger } from 'smorg-utils';

logger.info('Hello, world!');
logger.error('Something went wrong', { error: 'details' });

2. Custom Logger

import { createLogger, LogLevel } from 'smorg-utils';

const appLogger = createLogger({
  level: LogLevel.DEBUG,
  name: 'MyApp'
});

appLogger.debug('Debugging info');
appLogger.info('Application started');

3. Production Configuration

import { createLogger, LogLevel, jsonFormatter } from 'smorg-utils/logger';
import { createRotatingFileTransport } from 'smorg-utils/logger/transports';

const productionLogger = createLogger({
  level: LogLevel.WARN,
  formatter: jsonFormatter,
  transport: createRotatingFileTransport({
    filename: 'app',
    dirname: './logs',
    dateRotation: true,
    maxFiles: 30,
    compress: true
  })
});

📚 Comprehensive Examples

New! We've created extensive real-world examples in the src/logger/examples/ directory:

Each example is fully documented with real-world scenarios and can be run with:

npx ts-node src/logger/examples/01-basic-usage.ts

📚 API Documentation

Core Logger

A high-performance, configurable logging utility.

Basic Example

import { Logger, LogLevel, simpleFormatter } from 'smorg-utils';

const logger = new Logger({
  level: LogLevel.INFO,
  formatter: simpleFormatter,
  context: { service: 'api' }
});

logger.info('Server started', { port: 3000 });
// Output: [2023-12-07T10:30:00.000Z] INFO  Server started {"service":"api","port":3000}

Configuration Options

interface LoggerConfig {
  level?: LogLevel | LogLevelName;          // Minimum log level
  formatter?: LogFormatter;                 // Custom formatter function
  transport?: LogTransport;                 // Custom transport function
  includeTimestamp?: boolean;               // Include timestamps (default: true)
  context?: Record<string, unknown>;        // Global context
  name?: string;                           // Logger name
}

Log Levels

enum LogLevel {
  DEBUG = 0,
  INFO = 1,
  WARN = 2,
  ERROR = 3,
  SILENT = 4
}

Express Integration

For Express.js applications, import the HTTP middleware utilities:

import { createLogger, createHttpLogger, simpleFormatter } from 'smorg-utils';

const logger = createLogger({
  formatter: simpleFormatter,
  context: { service: 'api' }
});

// Create HTTP middleware for request/response logging
const httpLogger = createHttpLogger(logger, {
  includeFields: {
    method: true,
    url: true,
    ip: true,
    userAgent: false,
  },
  statusCodeLevels: {
    success: 'info',
    clientError: 'warn', 
    serverError: 'error',
  },
  skip: (req, res) => req.url === '/health'
});

// Add to Express app
app.use(httpLogger.requestLogger);
app.use(httpLogger.errorLogger);

File Logging with Rotation

For production applications needing file logging:

import { createLogger, createRotatingFileTransport } from 'smorg-utils';

const logger = createLogger({
  transport: createRotatingFileTransport({
    filename: 'app',
    dirname: './logs',
    dateRotation: true,     // Daily rotation
    maxFiles: 30,          // Keep 30 days
    compress: true,        // Compress old logs
    maxSize: 10 * 1024 * 1024  // 10MB max size
  })
});

// Separate files by log level
import { createMultiLevelFileTransport } from 'smorg-utils';

const multiLogger = createLogger({
  transport: createMultiLevelFileTransport({
    filename: 'app',
    dirname: './logs/by-level'
  })
});

Advanced Production Setup

import {
  createLogger,
  createHttpLogger,
  createRotatingFileTransport,
  LogLevel,
  simpleFormatter
} from 'smorg-utils';

const isProduction = process.env.NODE_ENV === 'production';

// Multi-transport logger
const logger = createLogger({
  level: isProduction ? LogLevel.INFO : LogLevel.DEBUG,
  transport: (message, level) => {
    // Console in development
    if (!isProduction) {
      console.log(simpleFormatter(level, message, new Date()));
    }
    
    // Always log to rotating files
    const fileTransport = createRotatingFileTransport({
      filename: 'app',
      dirname: './logs',
      dateRotation: true,
      maxFiles: 30,
      compress: true
    });
    
    fileTransport(message, level);
  },
  context: { 
    service: 'api',
    instance: process.env.INSTANCE_ID,
    version: process.env.APP_VERSION
  }
});

// Production-ready HTTP logging
const httpLogger = createHttpLogger(logger, {
  includeFields: {
    method: true,
    url: true,
    ip: true,
    userAgent: isProduction,
    headers: !isProduction
  },
  skip: (req, res) => {
    return isProduction && (
      req.url.startsWith('/health') ||
      req.url.startsWith('/static')
    );
  }
});

app.use(httpLogger.requestLogger);
app.use(httpLogger.errorLogger);

Factory Functions

createLogger(config?: LoggerConfig): ILogger

Creates a new logger instance with optional configuration.

import { createLogger, LogLevel } from 'smorg-utils';

const logger = createLogger({
  level: LogLevel.WARN,
  name: 'MyService'
});

createNoopLogger(): ILogger

Creates a logger that discards all messages (useful for testing).

import { createNoopLogger } from 'smorg-utils';

const logger = createNoopLogger();
logger.info('This will not be logged');

Child Loggers

Create child loggers with inherited context:

import { createLogger } from 'smorg-utils';

const parentLogger = createLogger({
  context: { service: 'api', version: '1.0.0' }
});

const requestLogger = parentLogger.child({ 
  requestId: 'req-123',
  userId: 'user-456' 
});

requestLogger.info('Processing request');
// Includes context from both parent and child

🆚 Migration from Monolithic Loggers

If you're migrating from a feature-rich logger that includes everything built-in:

Before (Monolithic Logger)

import Logger from './logger';  // 20-30KB bundle

app.use(Logger.requestLogger);
app.use(Logger.errorLogger);

After (Our Modular Approach)

// Import only what you need (~8-12KB total)
import { 
  createLogger, 
  createHttpLogger,
  createRotatingFileTransport 
} from 'smorg-utils';

const logger = createLogger({
  transport: createRotatingFileTransport({
    filename: 'app',
    dirname: './logs',
    dateRotation: true
  })
});

const httpLogger = createHttpLogger(logger);
app.use(httpLogger.requestLogger);
app.use(httpLogger.errorLogger);

🏗️ Build Configuration

This package supports multiple module formats:

ESM (Recommended)

import { Logger } from 'smorg-utils';

CommonJS

const { Logger } = require('smorg-utils');

Deep Imports (Tree-shaking)

// Import specific utilities only
import { createLogger } from 'smorg-utils/logger';
import { createHttpLogger } from 'smorg-utils/middlewares/express-logger';

📊 Bundle Size

This package is optimized for minimal bundle size:

| Import Pattern | Bundle Size | Features | |---------------|-------------|----------| | Core logger only | ~4KB | Basic logging | | + Express middleware | ~8KB | HTTP request/response logging | | + File transports | ~12KB | File logging with rotation | | Full package | ~15KB | All features |

Compare this to monolithic loggers that often bundle 20-30KB+ regardless of usage.

🧪 Testing

The package includes comprehensive tests and utilities for testing:

import { createNoopLogger } from 'smorg-utils';

// Use in tests to suppress log output
const logger = createNoopLogger();

🤝 Contributing

Contributions are welcome! Please read our contributing guidelines and ensure:

  1. All tests pass (npm test)
  2. Code is properly formatted (npm run format)
  3. No linting errors (npm run lint)
  4. TypeScript compiles without errors (npm run type-check)

📄 License

MIT © [Your Name]

🔄 Changelog

1.0.0

  • Initial release
  • Core logger with full TypeScript support
  • Express middleware utilities
  • File transport with rotation
  • Tree-shaking support
  • Dual module format (ESM/CJS)
  • Comprehensive test coverage