Skip to content

Commit

Permalink
feat: add shmancy reporter
Browse files Browse the repository at this point in the history
Named after Fancy Shmancy (something expensive and impressive) it extends the Fancy reporter and allows you to set a custom log format using sprintf expressions
  • Loading branch information
pimlie committed Oct 10, 2018
1 parent 3884e42 commit dc6121a
Show file tree
Hide file tree
Showing 6 changed files with 57 additions and 34 deletions.
47 changes: 31 additions & 16 deletions demo/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,34 +6,49 @@ const Consola = esm('../src')

const reporters = [
'FancyReporter',
'ShmancyReporter',
'BasicReporter',
'JSONReporter',
'WinstonReporter'
]

for (const reporter of reporters) {
const s = process.hrtime()
const consola = new Consola.Consola({
level: 5,
reporters: [new Consola[reporter]()]
reporters: [new Consola[reporter]({
errStream: process.stdout
})]
})

for (let type of Object.keys(consola.types).sort()) {
consola[type](`A message with consola.${type}()`)
}

consola.info('A JSON Log:', {
name: 'Cat',
color: '#454545'
})
for (let i = 0; i < 10; i++) {
for (let type of Object.keys(consola.types).sort()) {
consola[type](`A message with consola.${type}()`)
}

if (reporter === 'FancyReporter') {
consola.success({
message: 'This is a fancy badge',
additional: 'With some additional info',
additionalColor: 'brown',
badge: true
consola.info('A JSON Log:', {
name: 'Cat',
color: '#454545'
})

if (reporter === 'FancyReporter' || reporter === 'SmancyReporter') {
consola.success({
message: 'This is a fancy badge',
additional: 'With some additional info',
additionalColor: 'brown',
badge: true
})
}

consola.error(new Error('Something bad happened!'))

const tagged = consola.create({ defaults: { tag: 'tagged' } })
for (let type of Object.keys(consola.types).sort()) {
tagged[type](`A tagged message with consola.${type}()`)
}
}

consola.error(new Error('Something bad happened!'))
const t = process.hrtime(s)

console.error(`${reporter} took ${Math.round((t[0] * 1e9 + t[1]) / 1e4) / 1e2}ms`) // eslint-disable-line no-console
}
1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@
"dependencies": {
"chalk": "^2.4.1",
"figures": "^2.0.0",
"printj": "^1.2.0",
"std-env": "^2.0.2"
},
"devDependencies": {
Expand Down
21 changes: 3 additions & 18 deletions src/reporters/fancy.js
Original file line number Diff line number Diff line change
@@ -1,25 +1,10 @@
import figures from 'figures'
import chalk from 'chalk'
import BasicReporter from './basic'
import { parseStack, align } from '../utils'
import { parseStack, align, chalkColor, chalkBgColor } from '../utils'

This comment has been minimized.

Copy link
@pi0

pi0 Oct 10, 2018

Member

I intentionally didn't move chalk dependent utils into utils, because rollup tree-shaking was not working. Do you confirm they are tree-shake in browser bundle?


function chalkColor (name) {
if (name[0] === '#') {
return chalk.hex(name)
}
return chalk[name] || chalk.keyword(name)
}

function chalkBgColor (name) {
if (name[0] === '#') {
return chalk.bgHex(name)
}
return chalk['bg' + name[0] + name.slice(1)] || chalk.bgKeyword(name)
}

const NS_SEPARATOR = chalk.blue(figures(' › '))
export const NS_SEPARATOR = chalkColor('blue')(figures(' › '))

const ICONS = {
export const ICONS = {
start: figures('●'),
info: figures('ℹ'),
success: figures('✔'),
Expand Down
1 change: 1 addition & 0 deletions src/reporters/index.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
export { default as BasicReporter } from './basic'
export { default as BrowserReporter } from './browser'
export { default as FancyReporter } from './fancy'
export { default as ShmancyReporter } from './shmancy'
export { default as JSONReporter } from './json'
export { default as WinstonReporter } from './winston'
16 changes: 16 additions & 0 deletions src/utils.js
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
import chalk from 'chalk'

export function isPlainObject (obj) {
return Object.prototype.toString.call(obj) === '[object Object]'
}
Expand Down Expand Up @@ -64,3 +66,17 @@ export function align (alignment, str, len, space = ' ') {
default: return str
}
}

export function chalkColor (name) {
if (name[0] === '#') {
return chalk.hex(name)
}
return chalk[name] || chalk.keyword(name)
}

export function chalkBgColor (name) {
if (name[0] === '#') {
return chalk.bgHex(name)
}
return chalk['bg' + name[0] + name.slice(1)] || chalk.bgKeyword(name)
}
5 changes: 5 additions & 0 deletions yarn.lock
Original file line number Diff line number Diff line change
Expand Up @@ -5542,6 +5542,11 @@ pretty-ms@^3.1.0:
dependencies:
parse-ms "^1.0.0"

printj@^1.2.0:
version "1.2.0"
resolved "https://registry.yarnpkg.com/printj/-/printj-1.2.0.tgz#852fca7283cdb82f3fd08d007bde701a224cc397"
integrity sha512-wQ6jPc72jVXX/qpP2/oDIPQ+ZJqvZGAZPm47LnBwzWTBssK1a/c9p09e/Pd1Nx4ACm+Ru86AT99nuiyOFT2zOQ==

private@^0.1.6, private@^0.1.8:
version "0.1.8"
resolved "https://registry.yarnpkg.com/private/-/private-0.1.8.tgz#2381edb3689f7a53d653190060fcf822d2f368ff"
Expand Down

8 comments on commit dc6121a

@pimlie
Copy link
Contributor Author

@pimlie pimlie commented on dc6121a Oct 10, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@pi0 Although I expected like you that using sprintf would be more expensive, it appears that currently FancyReporter is about 1.6 times slower then ShmancyReporter (see the adapted demo in this PR)

This is partly because of the lots of writes in FancyReporter (in my tests it could be 10% faster if there was only one call to write) but also the color cache I (had to) use with Shmancy provides a great performance boost.

@pimlie
Copy link
Contributor Author

@pimlie pimlie commented on dc6121a Oct 10, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah, forgot to add shmancy self, see 2929648

@pi0
Copy link
Member

@pi0 pi0 commented on dc6121a Oct 10, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@pimlie We can batch all write operations into a single call. Will do it. BTW if it is going to be an standard to support printf, we can add some utils into Basic reporter instead of introducing a new reporter.

@pimlie
Copy link
Contributor Author

@pimlie pimlie commented on dc6121a Oct 10, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If we would use printf by default we also need to add the date. Would probably be nice to be able to set a custom date format as well then (toLocaleFormat instead of toLocaleTimeString).

If I remove all color stuff from Shmancy, its ~25% slower then Basic (26ms vs 20ms for 10 demo iterations). Let me know if you want me to put the printf stuff in Basic and just keep Basic/Fancy as we have.

@pi0
Copy link
Member

@pi0 pi0 commented on dc6121a Oct 10, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@pimlie I think that small diffs are not that important. But I agree to add time formatting option.

@pimlie
Copy link
Contributor Author

@pimlie pimlie commented on dc6121a Oct 10, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Great, will remove shmancy then and incorporate printf in basic and set default formats for basic + fancy.

@pimlie
Copy link
Contributor Author

@pimlie pimlie commented on dc6121a Oct 10, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would you mind to use moment.js for formatting the datetime? It seems there is no vanilla date formatter which works consistently along all browsers.

@pi0
Copy link
Member

@pi0 pi0 commented on dc6121a Oct 10, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@pimlie Moment is too big! Maybe dayjs or an equalant with es support. Also browser implementation is separated.

Please sign in to comment.