Blyp Docs

Winston -> Blyp

If your current setup centers on winston.createLogger(...), custom transports, and formatter pipelines, Blyp gives you a simpler model: structured logs by default, first-party request logging for frameworks, built-in file logging and rotation, and connector delivery without transport object sprawl.

Why Blyp can be better than Winston

If you already feel friction from custom Winston formats, multiple transports, or inconsistent request logging, that is usually the signal that the migration is worth it.

Install

Install @blyp/core with your package manager:

# Bun (recommended)
bun add @blyp/core

# npm
npm install @blyp/core

# pnpm
pnpm add @blyp/core

# yarn
yarn add @blyp/core

Let AI do the migration first

Before doing this by hand, give your AI workflow the Blyp migration references:

That gives the model the Winston-to-Blyp mapping up front, which is useful for bulk replacements across a large codebase. After that, use the manual guide below to review the resulting structure and the behavior changes.

Most common replacement

Winston

import winston from "winston";

const logger = winston.createLogger({
  level: "info",
  transports: [
    new winston.transports.File({ filename: "logs/app.log" }),
  ],
});

Blyp

import { createStandaloneLogger } from "@blyp/core";

const logger = createStandaloneLogger({
  level: "info",
  destination: "file",
});

If you just want the shared root logger, use the named export:

import { logger } from "@blyp/core";

API equivalents

WinstonBlyp equivalent
winston.createLogger({ level: "info" })logger or createStandaloneLogger({ level: "info" })
winston.transports.Filedestination: "file" with optional file.rotation config
winston.transports.Httpconnector config under connectors, such as Better Stack, Sentry, PostHog, or OTLP
logger.child({ requestId })logger.child({ requestId }) for stable bindings, or a framework adapter request logger for request-scoped logging
format.combine(...), format.json(), custom formattersstructured fields on each log call, or batched payloads with createStructuredLog()

For example, a Winston formatter pipeline often becomes structured fields instead of string rewriting:

import { createStructuredLog, logger } from "@blyp/core";

logger.info("user login", {
  userId: "usr_123",
  tenantId: "tenant_456",
});

const structuredLog = createStructuredLog("checkout", {
  requestId: "req_123",
});

structuredLog.set({
  user: { id: "usr_123" },
  payment: { provider: "stripe", status: "authorized" },
});

structuredLog.emit({
  level: "info",
  message: "checkout completed",
  status: 200,
});

Behavioral differences

For request logging, Winston child loggers are not the main migration target. Use the appropriate framework adapter, such as createLogger() from @blyp/core/express or @blyp/core/fastify, when the old app created request-local loggers in middleware.