Skip to main content
The Logger plugin provides comprehensive logging for CallApi requests and responses. It helps you debug API calls, monitor performance, and track errors during development and production.

Installation

The logger plugin is available as a separate package:
npm install @zayne-labs/callapi-plugins

Basic Usage

import { createFetchClient } from "@zayne-labs/callapi";
import { loggerPlugin } from "@zayne-labs/callapi-plugins";

const api = createFetchClient({
  baseURL: "https://api.example.com",
  plugins: [loggerPlugin()],
});

// All requests will now be logged
const { data } = await api("/users");

Configuration

LoggerOptions

EnabledOptions

Examples

Basic Logging

import { loggerPlugin } from "@zayne-labs/callapi-plugins";

const api = createFetchClient({
  baseURL: "https://api.example.com",
  plugins: [loggerPlugin()],
});

// Logs:
// → Request being sent to: https://api.example.com/users
// ✓ Request succeeded! { users: [...] }

Verbose Mode

import { loggerPlugin } from "@zayne-labs/callapi-plugins";

const api = createFetchClient({
  plugins: [
    loggerPlugin({
      mode: "verbose",
    }),
  ],
});

// In verbose mode, errors include full error data
const result = await api("/users/invalid");
// Logs:
// → Request being sent to: https://api.example.com/users/invalid
// ✗ GET request to '...' failed with status: 404 (Not Found)
//   Reason = "HTTPError: Not Found"
//   ErrorData: { message: "User not found", code: "USER_NOT_FOUND" }

Selective Logging

import { loggerPlugin } from "@zayne-labs/callapi-plugins";

const api = createFetchClient({
  plugins: [
    loggerPlugin({
      enabled: {
        onRequest: true,
        onError: true,
        onSuccess: false, // Don't log successful responses
        onRetry: true,
      },
    }),
  ],
});

Disable in Production

import { loggerPlugin } from "@zayne-labs/callapi-plugins";

const api = createFetchClient({
  plugins: [
    loggerPlugin({
      enabled: process.env.NODE_ENV !== "production",
    }),
  ],
});

Custom Console Object

import { loggerPlugin } from "@zayne-labs/callapi-plugins";

const customLogger = {
  log: (message: string, ...args: unknown[]) => {
    // Custom log implementation
    console.log(`[API] ${message}`, ...args);
  },
  error: (message: string, ...args: unknown[]) => {
    // Send errors to monitoring service
    monitoringService.error(message, ...args);
    console.error(`[API ERROR] ${message}`, ...args);
  },
  warn: (message: string, ...args: unknown[]) => {
    console.warn(`[API WARN] ${message}`, ...args);
  },
  success: (message: string, ...args: unknown[]) => {
    console.log(`[API SUCCESS] ${message}`, ...args);
  },
};

const api = createFetchClient({
  plugins: [
    loggerPlugin({
      consoleObject: customLogger,
    }),
  ],
});

Environment-Specific Configuration

import { loggerPlugin } from "@zayne-labs/callapi-plugins";

const getLoggerConfig = () => {
  if (process.env.NODE_ENV === "development") {
    return {
      mode: "verbose" as const,
      enabled: true,
    };
  }
  
  if (process.env.NODE_ENV === "test") {
    return {
      enabled: false,
    };
  }
  
  // Production: only log errors
  return {
    enabled: {
      onError: true,
      onRequest: false,
      onSuccess: false,
    },
  };
};

const api = createFetchClient({
  plugins: [loggerPlugin(getLoggerConfig())],
});

Log Output Examples

Request Log

Request being sent to: https://api.example.com/users/123

Success Log

✓ Request succeeded! { id: 123, name: "John Doe" }

HTTP Error (Basic Mode)

✗ GET request to 'https://api.example.com/users/999' failed with status: 404 (Not Found)
Reason = "HTTPError: User not found"

HTTP Error (Verbose Mode)

✗ GET request to 'https://api.example.com/users/999' failed with status: 404 (Not Found)
Reason = "HTTPError: User not found"
ErrorData: { message: "User not found", code: "USER_NOT_FOUND", requestId: "abc123" }

Validation Error (Basic Mode)

✗ (BODY) Validation for request to 'https://api.example.com/users' failed!
ValidationError: ✖ Expected string, received number → at email | ✖ String must contain at least 2 character(s) → at name

Validation Error (Verbose Mode)

✗ (BODY) Validation for request to 'https://api.example.com/users' failed!
ValidationError: ✖ Expected string, received number → at email | ✖ String must contain at least 2 character(s) → at name
Issues: [
  { path: ["email"], message: "Expected string, received number" },
  { path: ["name"], message: "String must contain at least 2 character(s)" }
]

Request Error

✗ POST to 'https://api.example.com/users' failed!
Reason = TypeError: Failed to fetch

Retry Log

Retrying request... Attempt: 2

Integration with Monitoring

import { loggerPlugin } from "@zayne-labs/callapi-plugins";
import * as Sentry from "@sentry/browser";

const monitoringLogger = {
  log: console.log,
  success: console.log,
  warn: console.warn,
  error: (message: string, ...args: unknown[]) => {
    // Send to monitoring service
    Sentry.captureMessage(message, {
      level: "error",
      extra: { args },
    });
    console.error(message, ...args);
  },
};

const api = createFetchClient({
  plugins: [
    loggerPlugin({
      consoleObject: monitoringLogger,
      mode: "verbose",
    }),
  ],
});

Combining with Other Plugins

import { loggerPlugin } from "@zayne-labs/callapi-plugins";
import { retryPlugin } from "./plugins/retry";

const api = createFetchClient({
  plugins: [
    loggerPlugin({
      enabled: {
        onRequest: true,
        onError: true,
        onRetry: true, // Log retry attempts
      },
    }),
    retryPlugin({ maxAttempts: 3 }),
  ],
});

// Will log:
// → Request being sent to: ...
// Retrying request... Attempt: 2
// Retrying request... Attempt: 3
// ✓ Request succeeded! ...

TypeScript

The logger plugin is fully typed:
import { loggerPlugin, type LoggerOptions } from "@zayne-labs/callapi-plugins";

const config: LoggerOptions = {
  mode: "verbose",
  enabled: {
    onRequest: true,
    onError: true,
  },
};

const api = createFetchClient({
  plugins: [loggerPlugin(config)],
});

See Also

Build docs developers (and LLMs) love