diff --git a/docs/transports.md b/docs/transports.md index 42e0c3c59..b79819f54 100644 --- a/docs/transports.md +++ b/docs/transports.md @@ -220,7 +220,7 @@ const transport = pino.transport({ pino(transport) ``` -The `options.destination` property may also be a number to represent a file descriptor. Typically this would be `1` to write to STDOUT or `2` to write to STDERR. If `options.destination` is not set, it defaults to `1` which means logs will be written to STDOUT. +The `options.destination` property may also be a number to represent a filedescriptor. Typically this would be `1` to write to STDOUT or `2` to write to STDERR. If `options.destination` is not set, it defaults to `1` which means logs will be written to STDOUT. If `options.destination` is a string integer, e.g. `'1'`, it will be coerced to a number and used as a file descriptor. If this is not desired, provide a full path, e.g. `/tmp/1`. The difference between using the `pino/file` transport builtin and using `pino.destination` is that `pino.destination` runs in the main thread, whereas `pino/file` sets up `pino.destination` in a worker thread. diff --git a/file.js b/file.js index 7968c1945..e824b9e36 100644 --- a/file.js +++ b/file.js @@ -4,7 +4,15 @@ const pino = require('./pino') const { once } = require('events') module.exports = async function (opts = {}) { - const destination = pino.destination({ dest: opts.destination || 1, sync: false }) + const destination = pino.destination({ dest: normalizeDest(opts.destination || 1), sync: false }) await once(destination, 'ready') return destination } + +function normalizeDest (destination) { + const fd = Number(destination) + if (typeof destination === 'string' && Number.isFinite(fd)) { + return fd + } + return destination +} diff --git a/test/fixtures/transport-string-stdout.js b/test/fixtures/transport-string-stdout.js new file mode 100644 index 000000000..64d8ac1ea --- /dev/null +++ b/test/fixtures/transport-string-stdout.js @@ -0,0 +1,9 @@ +'use strict' + +const pino = require('../..') +const transport = pino.transport({ + target: 'pino/file', + options: { destination: '1' } +}) +const logger = pino(transport) +logger.info('Hello') diff --git a/test/transport/core.test.js b/test/transport/core.test.js index b0853ed51..b12fa1b81 100644 --- a/test/transport/core.test.js +++ b/test/transport/core.test.js @@ -305,6 +305,18 @@ test('stdout in worker', async ({ not }) => { not(strip(actual).match(/Hello/), null) }) +test('string integer destination', async ({ not }) => { + let actual = '' + const child = execa(process.argv[0], [join(__dirname, '..', 'fixtures', 'transport-string-stdout.js')]) + + child.stdout.pipe(writer((s, enc, cb) => { + actual += s + cb() + })) + await once(child, 'close') + not(strip(actual).match(/Hello/), null) +}) + test('pino transport options with target', async ({ teardown, same }) => { const destination = join( os.tmpdir(),