diff --git a/.github/workflows/dev.yml b/.github/workflows/dev.yml new file mode 100644 index 0000000..3b07263 --- /dev/null +++ b/.github/workflows/dev.yml @@ -0,0 +1,75 @@ +name: dev +on: + pull_request: + push: + branches: + - master + - main +env: + CI: true + +jobs: + prettier: + name: Format code + runs-on: ubuntu-latest + if: ${{ github.event_name == 'push' }} + + steps: + - name: Checkout + uses: actions/checkout@v2 + + - name: Prettier + uses: gulpjs/prettier_action@v3.0 + with: + commit_message: 'chore: Run prettier' + prettier_options: '--write .' + + test: + name: Tests for Node ${{ matrix.node }} on ${{ matrix.os }} + runs-on: ${{ matrix.os }} + + strategy: + fail-fast: false + matrix: + node: [10, 12, 14, 16] + os: [ubuntu-latest, windows-latest, macos-latest] + + steps: + - name: Clone repository + uses: actions/checkout@v2 + + - name: Set Node.js version + uses: actions/setup-node@v2 + with: + node-version: ${{ matrix.node }} + + - run: node --version + - run: npm --version + + - name: Install npm dependencies + run: npm install + + - name: Run lint + run: npm run lint + + - name: Run tests + run: npm test + + - name: Coveralls + uses: coverallsapp/github-action@v1.1.2 + with: + github-token: ${{ secrets.GITHUB_TOKEN }} + flag-name: ${{matrix.os}}-node-${{ matrix.node }} + parallel: true + + coveralls: + needs: test + name: Finish up + + runs-on: ubuntu-latest + steps: + - name: Coveralls Finished + uses: coverallsapp/github-action@v1.1.2 + with: + github-token: ${{ secrets.GITHUB_TOKEN }} + parallel-finished: true diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml new file mode 100644 index 0000000..8a10ce3 --- /dev/null +++ b/.github/workflows/release.yml @@ -0,0 +1,17 @@ +name: release +on: + push: + branches: + - master + - main + +jobs: + release-please: + runs-on: ubuntu-latest + steps: + - uses: GoogleCloudPlatform/release-please-action@v2 + with: + token: ${{ secrets.GITHUB_TOKEN }} + release-type: node + package-name: release-please-action + bump-minor-pre-major: true diff --git a/.gitignore b/.gitignore index 6f63646..aa0c563 100644 --- a/.gitignore +++ b/.gitignore @@ -1,11 +1,15 @@ # Logs logs *.log +npm-debug.log* +yarn-debug.log* +yarn-error.log* # Runtime data pids *.pid *.seed +*.pid.lock # Directory for instrumented libs generated by jscoverage/JSCover lib-cov @@ -13,19 +17,51 @@ lib-cov # Coverage directory used by tools like istanbul coverage -# Grunt intermediate storage (http://gruntjs.com/creating-plugins#storing-task-files) +# nyc test coverage +.nyc_output + +# Grunt intermediate storage (https://gruntjs.com/creating-plugins#storing-task-files) .grunt -# Compiled binary addons (http://nodejs.org/api/addons.html) +# Bower dependency directory (https://bower.io/) +bower_components + +# node-waf configuration +.lock-wscript + +# Compiled binary addons (https://nodejs.org/api/addons.html) build/Release -# Dependency directory -# Commenting this out is preferred by some people, see -# https://www.npmjs.org/doc/misc/npm-faq.html#should-i-check-my-node_modules-folder-into-git- -node_modules +# Dependency directories +node_modules/ +jspm_packages/ -# Users Environment Variables -.lock-wscript +# TypeScript v1 declaration files +typings/ + +# Optional npm cache directory +.npm + +# Optional eslint cache +.eslintcache + +# Optional REPL history +.node_repl_history + +# Output of 'npm pack' +*.tgz + +# Yarn Integrity file +.yarn-integrity + +# dotenv environment variables file +.env + +# next.js build output +.next # Garbage files .DS_Store + +# Test results +test.xunit diff --git a/.prettierignore b/.prettierignore new file mode 100644 index 0000000..c96ebe0 --- /dev/null +++ b/.prettierignore @@ -0,0 +1,3 @@ +coverage/ +.nyc_output/ +CHANGELOG.md diff --git a/.travis.yml b/.travis.yml deleted file mode 100644 index 7e14b19..0000000 --- a/.travis.yml +++ /dev/null @@ -1,11 +0,0 @@ -sudo: false -language: node_js -node_js: - - '10' - - '8' - - '6' - - '4' - - '0.12' - - '0.10' -after_script: - - npm run coveralls diff --git a/LICENSE b/LICENSE index 3a58630..2fb3e72 100644 --- a/LICENSE +++ b/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2014, 2015, 2018 Blaine Bublitz and Eric Schoffstall +Copyright (c) 2014, 2015, 2018, 2021 Blaine Bublitz and Eric Schoffstall Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/README.md b/README.md index 33ef5c1..c4a6bfd 100644 --- a/README.md +++ b/README.md @@ -1,12 +1,12 @@

- +

# fancy-log -[![NPM version][npm-image]][npm-url] [![Downloads][downloads-image]][npm-url] [![Travis Build Status][travis-image]][travis-url] [![AppVeyor Build Status][appveyor-image]][appveyor-url] [![Coveralls Status][coveralls-image]][coveralls-url] [![Gitter chat][gitter-image]][gitter-url] +[![NPM version][npm-image]][npm-url] [![Downloads][downloads-image]][npm-url] [![Build Status][ci-image]][ci-url] [![Coveralls Status][coveralls-image]][coveralls-url] Log things, prefixed with a timestamp. @@ -54,18 +54,14 @@ current time in HH:MM:ss format. MIT -[downloads-image]: http://img.shields.io/npm/dm/fancy-log.svg + +[downloads-image]: https://img.shields.io/npm/dm/fancy-log.svg?style=flat-square [npm-url]: https://www.npmjs.com/package/fancy-log -[npm-image]: http://img.shields.io/npm/v/fancy-log.svg +[npm-image]: https://img.shields.io/npm/v/fancy-log.svg?style=flat-square -[travis-url]: https://travis-ci.org/gulpjs/fancy-log -[travis-image]: http://img.shields.io/travis/gulpjs/fancy-log.svg?label=travis-ci - -[appveyor-url]: https://ci.appveyor.com/project/gulpjs/fancy-log -[appveyor-image]: https://img.shields.io/appveyor/ci/gulpjs/fancy-log.svg?label=appveyor +[ci-url]: https://github.com/gulpjs/fancy-log/actions?query=workflow:dev +[ci-image]: https://img.shields.io/github/workflow/status/gulpjs/fancy-log/dev?style=flat-square [coveralls-url]: https://coveralls.io/r/gulpjs/fancy-log -[coveralls-image]: http://img.shields.io/coveralls/gulpjs/fancy-log/master.svg - -[gitter-url]: https://gitter.im/gulpjs/gulp -[gitter-image]: https://badges.gitter.im/gulpjs/gulp.svg +[coveralls-image]: https://img.shields.io/coveralls/gulpjs/fancy-log/master.svg?style=flat-square + diff --git a/appveyor.yml b/appveyor.yml deleted file mode 100644 index bd65027..0000000 --- a/appveyor.yml +++ /dev/null @@ -1,26 +0,0 @@ -# http://www.appveyor.com/docs/appveyor-yml -# http://www.appveyor.com/docs/lang/nodejs-iojs - -environment: - matrix: - # node.js - - nodejs_version: "0.10" - - nodejs_version: "0.12" - - nodejs_version: "4" - - nodejs_version: "6" - - nodejs_version: "8" - - nodejs_version: "10" - -install: - - ps: Install-Product node $env:nodejs_version - - npm install - -test_script: - - node --version - - npm --version - - cmd: npm test - -build: off - -# build version format -version: "{build}" diff --git a/index.js b/index.js index 9dc9888..be39922 100644 --- a/index.js +++ b/index.js @@ -4,27 +4,12 @@ var Console = require('console').Console; var gray = require('ansi-gray'); var timestamp = require('time-stamp'); var supportsColor = require('color-support'); -var nodeVersion = require('parse-node-version')(process.version); -var colorDetectionOptions = { - // If on Windows, ignore the isTTY check - // This is due to AppVeyor (and thus probably common Windows platforms?) failing the check - // TODO: If this is too broad, we can reduce it to an APPVEYOR env check - ignoreTTY: (process.platform === 'win32'), -}; - -// Needed to add this because node 10 decided to start coloring log output randomly -var console; -if (nodeVersion.major >= 10) { - // Node 10 also changed the way this is constructed - console = new Console({ - stdout: process.stdout, - stderr: process.stderr, - colorMode: false, - }); -} else { - console = new Console(process.stdout, process.stderr); -} +var console = new Console({ + stdout: process.stdout, + stderr: process.stderr, + colorMode: false, +}); function hasFlag(flag) { return (process.argv.indexOf('--' + flag) !== -1); @@ -39,7 +24,7 @@ function addColor(str) { return gray(str); } - if (supportsColor(colorDetectionOptions)) { + if (supportsColor()) { return gray(str); } diff --git a/package.json b/package.json index e9a70bb..f2e719c 100644 --- a/package.json +++ b/package.json @@ -10,7 +10,7 @@ "repository": "gulpjs/fancy-log", "license": "MIT", "engines": { - "node": ">= 0.10" + "node": ">=10.13.0" }, "main": "index.js", "files": [ @@ -20,23 +20,31 @@ "scripts": { "lint": "eslint .", "pretest": "npm run lint", - "test": "mocha --async-only", - "cover": "istanbul cover _mocha --report lcovonly", - "coveralls": "npm run cover && istanbul-coveralls" + "test": "nyc mocha --async-only" }, "dependencies": { "ansi-gray": "^0.1.1", "color-support": "^1.1.3", - "parse-node-version": "^1.0.0", - "time-stamp": "^1.0.0" + "time-stamp": "^2.2.0" }, "devDependencies": { - "eslint": "^2.13.0", - "eslint-config-gulp": "^3.0.1", - "expect": "^1.20.2", - "istanbul": "^0.4.3", - "istanbul-coveralls": "^1.0.3", - "mocha": "^3.5.3" + "eslint": "^7.32.0", + "eslint-config-gulp": "^5.0.1", + "eslint-plugin-node": "^11.1.0", + "expect": "^27.4.2", + "mocha": "^8.4.0", + "nyc": "^15.1.0", + "parse-node-version": "^2.0.0", + "sinon": "^12.0.1" + }, + "nyc": { + "reporter": [ + "lcov", + "text-summary" + ] + }, + "prettier": { + "singleQuote": true }, "keywords": [ "console.log", diff --git a/test/.eslintrc b/test/.eslintrc deleted file mode 100644 index 06b940f..0000000 --- a/test/.eslintrc +++ /dev/null @@ -1,3 +0,0 @@ -{ - "extends": "gulp/test" -} diff --git a/test/index.js b/test/index.js index 0efa484..e29b7fe 100644 --- a/test/index.js +++ b/test/index.js @@ -1,15 +1,28 @@ 'use strict'; +// Enable color as a normal terminal even on CI environment. +if (process.env.CI) { + process.stdout.isTTY = true; + process.env.CI = ''; + process.env.COLORTERM = true; +} + +// Node.js >=v12 removes escaped quotes in inspect string by: +// https://github.com/nodejs/node/pull/21624 +var nodeVersion = require('parse-node-version')(process.version); +var isLessThanNode12 = (nodeVersion.major < 12); + var util = require('util'); var expect = require('expect'); +var sinon = require('sinon'); var gray = require('ansi-gray'); var timestamp = require('time-stamp'); var log = require('../'); -var stdoutSpy = expect.spyOn(process.stdout, 'write').andCallThrough(); -var stderrSpy = expect.spyOn(process.stderr, 'write').andCallThrough(); +var stdoutSpy = sinon.spy(process.stdout, 'write'); +var stderrSpy = sinon.spy(process.stderr, 'write'); describe('log()', function() { @@ -17,15 +30,19 @@ describe('log()', function() { var colorterm = process.env.COLORTERM; beforeEach(function(done) { - stdoutSpy.reset(); + stdoutSpy.resetHistory(); done(); }); it('should work i guess', function(done) { log(1, 2, 3, 4, 'five'); var time = timestamp('HH:mm:ss'); - expect(stdoutSpy.calls[0].arguments).toInclude('[' + gray(time) + '] '); - expect(stdoutSpy.calls[1].arguments).toInclude('1 2 3 4 \'five\'\n'); + expect(stdoutSpy.args[0][0]).toEqual('[' + gray(time) + '] '); + if (isLessThanNode12) { + expect(stdoutSpy.args[1][0]).toEqual('1 2 3 4 \'five\'\n'); + } else { + expect(stdoutSpy.args[1][0]).toEqual('1 2 3 4 five\n'); + } done(); }); @@ -33,8 +50,8 @@ describe('log()', function() { it('should accept formatting', function(done) { log('%s %d %j', 'something', 0.1, { key: 'value' }); var time = timestamp('HH:mm:ss'); - expect(stdoutSpy.calls[0].arguments).toInclude('[' + gray(time) + '] '); - expect(stdoutSpy.calls[1].arguments).toInclude('something 0.1 {\"key\":\"value\"}\n'); + expect(stdoutSpy.args[0][0]).toEqual('[' + gray(time) + '] '); + expect(stdoutSpy.args[1][0]).toEqual('something 0.1 {"key":"value"}\n'); done(); }); @@ -44,8 +61,12 @@ describe('log()', function() { log(1, 2, 3, 4, 'five'); var time = timestamp('HH:mm:ss'); - expect(stdoutSpy.calls[0].arguments).toInclude('[' + time + '] '); - expect(stdoutSpy.calls[1].arguments).toInclude('1 2 3 4 \'five\'\n'); + expect(stdoutSpy.args[0][0]).toEqual('[' + time + '] '); + if (isLessThanNode12) { + expect(stdoutSpy.args[1][0]).toEqual('1 2 3 4 \'five\'\n'); + } else { + expect(stdoutSpy.args[1][0]).toEqual('1 2 3 4 five\n'); + } process.argv.pop(); @@ -57,8 +78,12 @@ describe('log()', function() { log(1, 2, 3, 4, 'five'); var time = timestamp('HH:mm:ss'); - expect(stdoutSpy.calls[0].arguments).toInclude('[' + gray(time) + '] '); - expect(stdoutSpy.calls[1].arguments).toInclude('1 2 3 4 \'five\'\n'); + expect(stdoutSpy.args[0][0]).toEqual('[' + gray(time) + '] '); + if (isLessThanNode12) { + expect(stdoutSpy.args[1][0]).toEqual('1 2 3 4 \'five\'\n'); + } else { + expect(stdoutSpy.args[1][0]).toEqual('1 2 3 4 five\n'); + } process.argv.pop(); @@ -71,8 +96,12 @@ describe('log()', function() { log(1, 2, 3, 4, 'five'); var time = timestamp('HH:mm:ss'); - expect(stdoutSpy.calls[0].arguments).toInclude('[' + time + '] '); - expect(stdoutSpy.calls[1].arguments).toInclude('1 2 3 4 \'five\'\n'); + expect(stdoutSpy.args[0][0]).toEqual('[' + time + '] '); + if (isLessThanNode12) { + expect(stdoutSpy.args[1][0]).toEqual('1 2 3 4 \'five\'\n'); + } else { + expect(stdoutSpy.args[1][0]).toEqual('1 2 3 4 five\n'); + } process.env.TERM = term; process.env.COLORTERM = colorterm; @@ -84,15 +113,19 @@ describe('log()', function() { describe('log.info()', function() { beforeEach(function(done) { - stdoutSpy.reset(); + stdoutSpy.resetHistory(); done(); }); it('should work i guess', function(done) { log.info(1, 2, 3, 4, 'five'); var time = timestamp('HH:mm:ss'); - expect(stdoutSpy.calls[0].arguments).toInclude('[' + gray(time) + '] '); - expect(stdoutSpy.calls[1].arguments).toInclude('1 2 3 4 \'five\'\n'); + expect(stdoutSpy.args[0][0]).toEqual('[' + gray(time) + '] '); + if (isLessThanNode12) { + expect(stdoutSpy.args[1][0]).toEqual('1 2 3 4 \'five\'\n'); + } else { + expect(stdoutSpy.args[1][0]).toEqual('1 2 3 4 five\n'); + } done(); }); @@ -100,8 +133,8 @@ describe('log.info()', function() { it('should accept formatting', function(done) { log.info('%s %d %j', 'something', 0.1, { key: 'value' }); var time = timestamp('HH:mm:ss'); - expect(stdoutSpy.calls[0].arguments).toInclude('[' + gray(time) + '] '); - expect(stdoutSpy.calls[1].arguments).toInclude('something 0.1 {\"key\":\"value\"}\n'); + expect(stdoutSpy.args[0][0]).toEqual('[' + gray(time) + '] '); + expect(stdoutSpy.args[1][0]).toEqual('something 0.1 {"key":"value"}\n'); done(); }); @@ -110,15 +143,15 @@ describe('log.info()', function() { describe('log.dir()', function() { beforeEach(function(done) { - stdoutSpy.reset(); + stdoutSpy.resetHistory(); done(); }); it('should format an object with util.inspect', function(done) { log.dir({ key: 'value' }); var time = timestamp('HH:mm:ss'); - expect(stdoutSpy.calls[0].arguments).toInclude('[' + gray(time) + '] '); - expect(stdoutSpy.calls[1].arguments).toInclude(util.inspect({ key: 'value' }) + '\n'); + expect(stdoutSpy.args[0][0]).toEqual('[' + gray(time) + '] '); + expect(stdoutSpy.args[1][0]).toEqual(util.inspect({ key: 'value' }) + '\n'); done(); }); @@ -127,15 +160,19 @@ describe('log.dir()', function() { describe('log.warn()', function() { beforeEach(function(done) { - stderrSpy.reset(); + stderrSpy.resetHistory(); done(); }); it('should work i guess', function(done) { log.warn(1, 2, 3, 4, 'five'); var time = timestamp('HH:mm:ss'); - expect(stderrSpy.calls[0].arguments).toInclude('[' + gray(time) + '] '); - expect(stderrSpy.calls[1].arguments).toInclude('1 2 3 4 \'five\'\n'); + expect(stderrSpy.args[0][0]).toEqual('[' + gray(time) + '] '); + if (isLessThanNode12) { + expect(stderrSpy.args[1][0]).toEqual('1 2 3 4 \'five\'\n'); + } else { + expect(stderrSpy.args[1][0]).toEqual('1 2 3 4 five\n'); + } done(); }); @@ -143,8 +180,8 @@ describe('log.warn()', function() { it('should accept formatting', function(done) { log.warn('%s %d %j', 'something', 0.1, { key: 'value' }); var time = timestamp('HH:mm:ss'); - expect(stderrSpy.calls[0].arguments).toInclude('[' + gray(time) + '] '); - expect(stderrSpy.calls[1].arguments).toInclude('something 0.1 {\"key\":\"value\"}\n'); + expect(stderrSpy.args[0][0]).toEqual('[' + gray(time) + '] '); + expect(stderrSpy.args[1][0]).toEqual('something 0.1 {"key":"value"}\n'); done(); }); @@ -153,15 +190,19 @@ describe('log.warn()', function() { describe('log.error()', function() { beforeEach(function(done) { - stderrSpy.reset(); + stderrSpy.resetHistory(); done(); }); it('should work i guess', function(done) { log.error(1, 2, 3, 4, 'five'); var time = timestamp('HH:mm:ss'); - expect(stderrSpy.calls[0].arguments).toInclude('[' + gray(time) + '] '); - expect(stderrSpy.calls[1].arguments).toInclude('1 2 3 4 \'five\'\n'); + expect(stderrSpy.args[0][0]).toEqual('[' + gray(time) + '] '); + if (isLessThanNode12) { + expect(stderrSpy.args[1][0]).toEqual('1 2 3 4 \'five\'\n'); + } else { + expect(stderrSpy.args[1][0]).toEqual('1 2 3 4 five\n'); + } done(); }); @@ -169,8 +210,8 @@ describe('log.error()', function() { it('should accept formatting', function(done) { log.error('%s %d %j', 'something', 0.1, { key: 'value' }); var time = timestamp('HH:mm:ss'); - expect(stderrSpy.calls[0].arguments).toInclude('[' + gray(time) + '] '); - expect(stderrSpy.calls[1].arguments).toInclude('something 0.1 {\"key\":\"value\"}\n'); + expect(stderrSpy.args[0][0]).toEqual('[' + gray(time) + '] '); + expect(stderrSpy.args[1][0]).toEqual('something 0.1 {"key":"value"}\n'); done(); });