From efc4b8837cfc2b52f0ea6441e4a89af381130830 Mon Sep 17 00:00:00 2001 From: anseki Date: Sun, 5 Apr 2015 14:45:42 +0900 Subject: [PATCH] Add `setDefault`. --- lib/readline-sync.js | 180 +++++++++++++++++++++++-------------------- 1 file changed, 97 insertions(+), 83 deletions(-) diff --git a/lib/readline-sync.js b/lib/readline-sync.js index 0e6e4bf..f5449e4 100644 --- a/lib/readline-sync.js +++ b/lib/readline-sync.js @@ -20,7 +20,7 @@ var childProc = require('child_process'), defaultOptions = { - prompt: '> ', // for API + prompt: '> ', noEchoBack: false, mask: '*', limit: '', @@ -36,7 +36,7 @@ var extHostPath, extHostArgs, tempdir, salt = 0; /* - display: string + display: other (to string) keyIn: boolean noEchoBack: boolean mask: string @@ -45,8 +45,8 @@ var noTrim: boolean encoding, bufSize, print */ -function readlineSync(options) { - var input = '', displaySave = options.display, +function _readlineSync(options) { + var input = '', displaySave = (options.display += ''), silent = !options.display && options.keyIn && options.noEchoBack && !options.mask; function tryExt() { @@ -196,7 +196,7 @@ function readlineSync(options) { setRawMode(false); })(); - if (typeof options.print === 'function' && !silent) { // must at least write '\n' + if (options.print && !silent) { // must at least write '\n' options.print(displaySave + (options.noEchoBack ? (new Array(input.length + 1)).join(options.mask) : input) + '\n', options.encoding); @@ -363,19 +363,17 @@ function getHostArgs(options) { } return extHostArgs.concat((function(conf) { - var args = [], key; - for (key in conf) { - if (conf.hasOwnProperty(key)) { - if (conf[key] === 'boolean') { - if (options[key]) { args.push('--' + key); } - } else if (conf[key] === 'string') { - if (options[key]) { - args.push('--' + key, - options.encoded ? encodeDOS(options[key]) : options[key]); - } + var args = []; + Object.keys(conf).forEach(function(optionName) { + if (conf[optionName] === 'boolean') { + if (options[optionName]) { args.push('--' + optionName); } + } else if (conf[optionName] === 'string') { + if (options[optionName]) { + args.push('--' + optionName, + options.encoded ? encodeDOS(options[optionName]) : options[optionName]); } } - } + }); return args; })({ display: 'string', @@ -388,10 +386,67 @@ function getHostArgs(options) { })); } +// margeOptions(options1, options2 ... ) +// margeOptions(true, options1, options2 ... ) // from defaultOptions function margeOptions() { - var optsHashes = Array.prototype.slice.call(arguments), - options = {}; - return options; + var optionsList = Array.prototype.slice.call(arguments), + optionNames, fromDefault; + + if (optionsList.length && typeof optionsList[0] === 'boolean') { + fromDefault = optionsList.shift(); + if (fromDefault) { + optionNames = Object.keys(defaultOptions); + optionsList.unshift(defaultOptions); + } + } + + return optionsList.reduce(function(options, optionsPart) { +/* jshint eqnull:true */ + if (optionsPart == null) { return options; } +/* jshint eqnull:false */ + + if (!fromDefault) { optionNames = Object.keys(optionsPart); } + optionNames.forEach(function(optionName) { + var value; + if (!optionsPart.hasOwnProperty(optionName)) { return; } + value = optionsPart[optionName]; + switch (optionName) { + // _readlineSync defaultOptions + // string + case 'mask': // * * + case 'limit': // * * + case 'encoding': // * * +/* jshint eqnull:true */ + options[optionName] = value != null ? value + '' : ''; +/* jshint eqnull:false */ + break; + // number + case 'bufSize': // * * + if (!isNaN(value = parseInt(value, 10)) && typeof value === 'number') + { options[optionName] = value; } + break; + // boolean + case 'noEchoBack': // * * + case 'caseSensitive': // * * + case 'noTrim': // * * + case 'keyIn': // * + options[optionName] = !!value; + break; + // function + case 'print': // * * + options[optionName] = typeof value === 'function' ? value : null; + break; + // other + case 'prompt': // * + case 'display': // * +/* jshint eqnull:true */ + options[optionName] = value != null ? value : ''; +/* jshint eqnull:false */ + break; + } + }); + return options; + }, {}); } function flattenArray(array, validate) { @@ -410,65 +465,17 @@ function flattenArray(array, validate) { // for dev exports._useExtSet = function(use) { useExt = use; }; -exports.setPrint = function(fnc) { defaultOptions.print = fnc; }; - -exports.setPrompt = function(newPrompt) { -/* jshint eqnull:true */ - if (newPrompt != null) { -/* jshint eqnull:false */ - defaultOptions.prompt = newPrompt; - } - return defaultOptions.prompt; -}; - -exports.setEncoding = function(newEncoding) { - if (typeof newEncoding === 'string') { - defaultOptions.encoding = newEncoding; - } - return defaultOptions.encoding; -}; - -exports.setMask = function(newMask) { - if (typeof newMask === 'string') { - defaultOptions.mask = newMask; - } - return defaultOptions.mask; -}; - -exports.setBufferSize = function(newBufSize) { - newBufSize = parseInt(newBufSize, 10); - if (!isNaN(newBufSize) && typeof newBufSize === 'number') { - defaultOptions.bufSize = newBufSize; - } - return defaultOptions.bufSize; -}; - exports.prompt = function(options) { - var readOptions = { - display: defaultOptions.prompt + '', - keyIn: false, - noEchoBack: !!(options && options.noEchoBack), - mask: defaultOptions.mask, - limit: '', - caseSensitive: !!(options && options.caseSensitive), - noTrim: !!(options && options.noTrim) - }; - return readlineSync(readOptions); + var readOptions = margeOptions(true, options); + readOptions.display = readOptions.prompt; + return _readlineSync(readOptions); }; exports.question = function(query, options) { - var readOptions = { -/* jshint eqnull:true */ - display: query != null ? query + '' : '', -/* jshint eqnull:false */ - keyIn: false, - noEchoBack: !!(options && options.noEchoBack), - mask: defaultOptions.mask, - limit: '', - caseSensitive: !!(options && options.caseSensitive), - noTrim: !!(options && options.noTrim) - }; - return readlineSync(readOptions); + var readOptions = margeOptions(margeOptions(true, options), { + display: query + }); + return _readlineSync(readOptions); }; exports.keyIn = function(query, options) { @@ -476,16 +483,23 @@ exports.keyIn = function(query, options) { flattenArray(options.limit, function(value) { return typeof value === 'string' || typeof value === 'number'; }) .join('').replace(/\n/g, '').replace(/[^A-Za-z0-9_ ]/g, '\\$&') : '', - readOptions = { -/* jshint eqnull:true */ - display: query != null ? query + '' : '', -/* jshint eqnull:false */ + readOptions = margeOptions(margeOptions(true, options), { + display: query, keyIn: true, - noEchoBack: !!(options && options.noEchoBack), - mask: defaultOptions.mask, limit: limit, - caseSensitive: !!(options && options.caseSensitive), noTrim: true - }; - return readlineSync(readOptions); + }); + return _readlineSync(readOptions); }; + +exports.setDefault = function(options) { + defaultOptions = margeOptions(true, options); + return margeOptions(true); // copy +}; + +// These APIs are now obsolete. +exports.setPrint = function(value) { return exports.setDefault({print: value}).print; }; +exports.setPrompt = function(value) { return exports.setDefault({prompt: value}).prompt; }; +exports.setEncoding = function(value) { return exports.setDefault({encoding: value}).encoding; }; +exports.setMask = function(value) { return exports.setDefault({mask: value}).mask; }; +exports.setBufferSize = function(value) { return exports.setDefault({bufSize: value}).bufSize; };