diff --git a/package.json b/package.json index eb04d301..75477b2c 100644 --- a/package.json +++ b/package.json @@ -12,6 +12,7 @@ "chalk": "^2.3.0", "fs-extra": "^5.0.0", "lodash": "^4.17.4", + "node-notifier": "^5.2.1", "password-prompt": "^1.0.4", "semver": "^5.5.0", "strip-ansi": "^4.0.0", diff --git a/src/index.ts b/src/index.ts index 1db41ef1..3721f6cc 100644 --- a/src/index.ts +++ b/src/index.ts @@ -5,6 +5,7 @@ import deps from './deps' import Errors, {CLIError, Options as ErrorOptions} from './errors' import {ExitError} from './exit' import * as Logger from './logger' +import notify from './notify' import Output from './output' import {IPromptOptions} from './prompt' import * as Table from './styled/table' @@ -31,6 +32,7 @@ export const scope = (_scope?: string) => { fatal: errors('fatal', _scope), exit(code = 1, error?: Error) { throw new ExitError(code, error) }, + notify, get prompt() { return deps.prompt.prompt }, get confirm() { return deps.prompt.confirm }, diff --git a/src/notify.ts b/src/notify.ts new file mode 100644 index 00000000..f8791d24 --- /dev/null +++ b/src/notify.ts @@ -0,0 +1,21 @@ +import Notifier = require('node-notifier') + +export default (opts: Notifier.Notification, cb?: Notifier.NotificationCallback) => { + const notifier: typeof Notifier = require('node-notifier') + return notifier.notify({ + // title: `heroku ${process.argv[2]}`, + // icon: path.join('Terminal Icon'), + // icon: path.join(__dirname, '../assets/heroku.png'), + // contentImage: path.join(__dirname, '../assets/heroku.png'), + // open: // URL to open on Click + // wait: false, // Wait for User Action against Notification or times out. Same as timeout = 5 seconds + + // New in latest version. See `example/macInput.js` for usage + // timeout: 5, // Takes precedence over wait if both are defined. + // closeLabel: void 0, // String. Label for cancel button + // actions: void 0, // String | Array. Action label or list of labels in case of dropdown + // dropdownLabel: void 0, // String. Label to be used if multiple actions + // reply: false // Boolean. If notification should take input. Value passed as third argument in callback and event emitter. + ...opts + }, cb) +} diff --git a/test/fancy.ts b/test/fancy.ts new file mode 100644 index 00000000..e84ecac7 --- /dev/null +++ b/test/fancy.ts @@ -0,0 +1,28 @@ +import chalk from 'chalk' +import {expect, fancy as base, FancyTypes, NockScope} from 'fancy-test' +import * as fs from 'fs-extra' +import * as path from 'path' + +import cli from '../src' + +export { + expect, + FancyTypes, + NockScope, +} + +let count = 0 +const logLevel = cli.config.logLevel + +export const fancy = base +.do(async (ctx: {count: number, base: string}) => { + ctx.count = count++ + ctx.base = path.join(__dirname, '../tmp', `test-${ctx.count}`) + await fs.remove(ctx.base) + cli.config.errlog = path.join(ctx.base, 'error.log') + chalk.enabled = false +}) +.finally(async () => { + cli.config.logLevel = logLevel + await cli.done() +}) diff --git a/test/notify.test.ts b/test/notify.test.ts new file mode 100644 index 00000000..dc54bfe5 --- /dev/null +++ b/test/notify.test.ts @@ -0,0 +1,11 @@ +import cli from '../src' + +import {fancy} from './fancy' + +describe('notify', () => { + fancy + .stderr() + .it('shows notification', (_, done) => { + cli.notify({message: 'example notification'}, done) + }) +})