Blank Transport
The built-in BlankTransport
allows you to quickly create custom transports by providing your own shipToLogger
function. This is perfect for simple custom logging logic, prototyping new transport ideas, or quick integrations with custom services.
TIP
If you want to create more advanced / complex transports, it is recommended you read the Creating Transports guide.
Installation
No additional packages needed beyond the core loglayer
package:
npm i loglayer
pnpm add loglayer
yarn add loglayer
Setup
import { LogLayer, BlankTransport } from 'loglayer'
const log = new LogLayer({
transport: new BlankTransport({
shipToLogger: ({ logLevel, messages, data, hasData }) => {
// Your custom logging logic here
console.log(`[${logLevel}]`, ...messages, data && hasData ? data : '');
// Return value is used for debugging when consoleDebug is enabled
return messages;
}
})
})
Configuration Options
shipToLogger
(Required)
The function that will be called to handle log shipping. This is the only required parameter for creating a custom transport.
- Type:
(params: LogLayerTransportParams) => any[]
- Required:
true
Return Value: The function must return an array (any[]
). This return value is used for debugging purposes when consoleDebug
is enabled - it will be logged to the console using the appropriate console method based on the log level.
The function receives a LogLayerTransportParams
object with these fields:
interface LogLayerTransportParams {
/**
* The log level of the message
*/
logLevel: LogLevel;
/**
* The parameters that were passed to the log message method (eg: info / warn / debug / error)
*/
messages: any[];
/**
* Object data such as metadata, context, and / or error data
*/
data?: Record<string, any>;
/**
* If true, the data object is included in the message parameters
*/
hasData?: boolean;
}
Message Parameters
The messages
parameter is an array because LogLayer supports multiple parameters for formatting. See the Basic Logging section for more details.
For example, if a user does the following:
logger.withMetadata({foo: 'bar'}).info('hello world', 'foo');
The parameters passed to shipToLogger
would be:
{
logLevel: 'info',
messages: ['hello world', 'foo'],
data: {foo: 'bar'},
hasData: true
}
level
Sets the minimum log level to process. Messages with a lower priority level will be ignored.
- Type:
"trace" | "debug" | "info" | "warn" | "error" | "fatal"
- Default:
"trace"
(processes all log levels)
enabled
If false, the transport will not send logs to the logger.
- Type:
boolean
- Default:
true
consoleDebug
If true, the transport will log to the console for debugging purposes.
- Type:
boolean
- Default:
false
When consoleDebug
is enabled, the return value from your shipToLogger
function will be logged to the console using the appropriate console method based on the log level (e.g., console.info()
for info logs, console.error()
for error logs, etc.).
This is useful for debugging your custom transport logic and seeing exactly what data is being processed.
Error Serialization
When using the BlankTransport, it's recommended to configure LogLayer with an errorSerializer
to ensure errors are properly serialized before being passed to your shipToLogger
function. The serialize-error
package is the recommended choice for consistent error serialization.
Installation
npm install serialize-error
yarn add serialize-error
pnpm add serialize-error
Usage
import { LogLayer, BlankTransport } from 'loglayer'
import serializeError from 'serialize-error'
const log = new LogLayer({
errorSerializer: serializeError,
transport: new BlankTransport({
shipToLogger: ({ logLevel, messages, data, hasData }) => {
console.log(`[${logLevel}]`, ...messages, data && hasData ? data : '');
return messages;
}
})
})
Before and After Example
Error Field Name
The error appears in data.err
by default, but this field name can be customized using the errorFieldName
configuration option. See the Error Handling Configuration section for more details.
Without errorSerializer:
const log = new LogLayer({
transport: new BlankTransport({
shipToLogger: ({ logLevel, messages, data, hasData }) => {
console.log(`[${logLevel}]`, ...messages, data && hasData ? data : '');
return messages;
}
})
})
log.withError(new Error('Database connection failed')).error('Failed to connect');
// Output: [error] Failed to connect { err: [Error: Database connection failed] }
With errorSerializer:
const log = new LogLayer({
errorSerializer: serializeError,
transport: new BlankTransport({
shipToLogger: ({ logLevel, messages, data, hasData }) => {
console.log(`[${logLevel}]`, ...messages, data && hasData ? data : '');
return messages;
}
})
})
log.withError(new Error('Database connection failed')).error('Failed to connect');
// Output: [error] Failed to connect {
// err: {
// name: 'Error',
// message: 'Database connection failed',
// stack: 'Error: Database connection failed\n at ...'
// }
// }
Examples
Simple Console Logging
import { LogLayer, BlankTransport } from 'loglayer'
const log = new LogLayer({
transport: new BlankTransport({
shipToLogger: ({ logLevel, messages, data, hasData }) => {
const timestamp = new Date().toISOString();
const message = messages.join(" ");
const dataStr = data && hasData ? ` | ${JSON.stringify(data)}` : '';
console.log(`[${timestamp}] [${logLevel.toUpperCase()}] ${message}${dataStr}`);
// Return value is used for debugging when consoleDebug is enabled
return messages;
}
})
})
log.withMetadata({ user: 'john' }).info('User logged in');
// Output: [2023-12-01T10:30:00.000Z] [INFO] User logged in | {"user":"john"}
Custom API Integration
import { LogLayer, BlankTransport } from 'loglayer'
const log = new LogLayer({
transport: new BlankTransport({
shipToLogger: ({ logLevel, messages, data, hasData }) => {
const payload = {
level: logLevel,
message: messages.join(" "),
timestamp: new Date().toISOString(),
...(data && hasData ? data : {})
};
// Send to your custom API
fetch('/api/logs', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(payload)
}).catch(err => {
console.error('Failed to send log to API:', err);
});
// Return value is used for debugging when consoleDebug is enabled
return messages;
}
})
})
Debug Mode
import { LogLayer, BlankTransport } from 'loglayer'
const log = new LogLayer({
transport: new BlankTransport({
consoleDebug: true // This will also log to console for debugging
shipToLogger: ({ logLevel, messages, data, hasData }) => {
// Your custom logic here
const payload = {
level: logLevel,
message: messages.join(" "),
...(data && hasData ? data : {})
};
// Send to external service
fetch('/api/logs', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(payload)
});
// Return value is used for debugging when consoleDebug is enabled
return messages;
},
})
})