case $input in
hello)
echo "You said hello"
;;
bye)
echo "You said bye"
if foo; then
bar
fi
;;
*)
echo "You said something weird..."
;;
esac
Really??
#!/usr/bin/env node
console.log("Hello World!");
$ chmod u+x myCLA
$(Node v4.2) ./myCLA
Hello World!
#!/usr/bin/env node
var userArgs = process.argv.slice(2);
var name = userArgs[0];
console.log("Hello " + name + "!");
$(Node v4.2) ./myCLA2 Josh
Hello Josh!
process.argv
is a no fun. Luckily, there's really no need...$ ./bin/pushfile -u README.md
console.log(process.argv);
//[ '/usr/local/Cellar/node/4.2.1/bin/node',
// '/Users/joshfinnie/src/personal/pushfile/bin/pushfile',
// '-u',
// 'README.md' ]
// Don't do this!
var userArgs = process.argv.slice(2);
var name = userArgs[0];
#!/usr/bin/env node
// Excerpt taken from Pushfile.
var opts = require('commander');
var version = require(__dirname + '/../package').version;
opts
.version(version)
.usage('[options] <file ...>')
.option('-u, --unique', 'Gives a unique hash for uploaded file.')
.option('-c, --configure', 'Create a configuration file.')
.option('-v, --version', 'Prints Version');
opts
.on('--help', function(){
console.log(' Examples:');
console.log('');
console.log(' $ pushfile -u <FILENAME>');
console.log(' $ pushfile <FILENAME>');
console.log(' $ pushfile -v');
console.log(' $ pushfile -c');
console.log('');
});
opts.parse(process.argv);
if (opts.configure) {
pushfile.createConfig();
}
else (optsLength > 0) {
pushfile.pushfile(opts.args[0], unique=opts.unique);
}
With commander.js
, user arguments are now easily accessible:
No need to hunt through the array of process.argv
for what the user inputted.
$ ./bin/pushfile -h
Usage: pushfile [options] <file ...>
Options:
-h, --help output usage information
-V, --version output the version number
-u, --unique Gives a unique hash for uploaded file.
-c, --configure Create a configuration file.
-v, --version Prints Version
Examples:
$ pushfile -u <FILENAME>
$ pushfile <FILENAME>
$ pushfile -v
$ pushfile -c
Also, commander.js
gives really slick --help
options out of the box:
The package.json
file:
{
...,
"devDependencies": {
"babel-core": "^6.1.2",
"babel-plugin-transform-es2015-modules-commonjs": "^6.1.3",
"babel-preset-es2015": "^6.1.2",
"babel-preset-stage-0": "^6.1.2",
"gulp": "^3.9.0",
"gulp-babel": "^6.1.0",
"gulp-concat": "^2.6.0",
"gulp-plumber": "^1.0.1",
"gulp-uglify": "^1.4.2",
...
}
}
The gulp.es6
file:
import gulp from 'gulp';
import babel from 'gulp-babel';
import plumber from 'gulp-plumber';
import uglify from 'gulp-uglify';
import concat from 'gulp-concat';
gulp.task('babel', () => {
gulp.src('src/*.es6')
.pipe(plumber())
.pipe(babel())
.pipe(gulp.dest('lib'));
});
gulp.task('minify', () => {
gulp.src('src/babel/*.js')
.pipe(plumber())
.pipe(concat('app.js'))
.pipe(uglify())
.pipe(gulp.dest('lib'));
})
gulp.task('watch', () => {
gulp.watch('src/*.es6', ['babel', 'minify'])
})
gulp.task('default', ['babel', 'minify', 'watch']);
The gulp.js
file:
require('babel-core/register');
require('./gulpfile.es6');
:-( (but it's getting better...)
Testing is awesome, since we are testing a Node.js app not a bash app... Take your pick:
Source: List_of_unit_testing_frameworks#JavaScript (Wikipedia)
import assert from 'assert';
let hashfile = require('../lib/hashfile');
describe('hashlib', () => {
it('should return proper hash of filename', () => {
hashfile.hash('test/test_of_long_file_name.json', 'test_salt', (result) => {
assert.equal('aNLAzajPvK.json', result);
});
});
it('should return same file extension', () => {
hashfile.hash('test/test_of_long_file_name.json', 'test_salt', (result) => {
assert.equal('json', result.split('.').pop());
});
});
it('should return a filename of only 10 charachers', () => {
hashfile.hash('test/test_of_long_file_name.json', 'test_salt', (result) => {
assert.equal(10, result.substr(0, result.lastIndexOf('.')).length);
});
});
});
Update your package.json file:
/// package.json
{
...,
"preferGlobal": true,
"bin": {"app": "bin/app"}
}
npm adduser
to set up user
$ npm adduser
Username: joshfinnie
Password:
Email: (this IS public) josh@jfin.us
npm shrinkwrap
in your project directory.
$ npm shrinkwrap
...
wrote npm-shrinkwrap.json
This command locks down the versions of a package's dependencies so that you can control exactly which versions of each dependency will be used when your package is installed. The package.json file is still required if you want to use npm install. [ 1]
{
...,
"prompt": {
"version": "0.2.14",
"from": "prompt@0.2.14",
"resolved": "https://registry.npmjs.org/prompt/-/prompt-0.2.14.tgz",
"dependencies": {
"pkginfo": {
"version": "0.3.1",
"from": "pkginfo@>=0.0.0 <1.0.0",
"resolved": "https://registry.npmjs.org/pkginfo/-/pkginfo-0.3.1.tgz"
},
...
"utile": {
"version": "0.2.1",
"from": "utile@>=0.2.0 <0.3.0",
"resolved": "https://registry.npmjs.org/utile/-/utile-0.2.1.tgz",
"dependencies": {
"async": {
"version": "0.2.10",
"from": "async@>=0.2.9 <0.3.0",
"resolved": "https://registry.npmjs.org/async/-/async-0.2.10.tgz"
},
"deep-equal": {
"version": "1.0.1",
"from": "deep-equal@*",
"resolved": "https://registry.npmjs.org/deep-equal/-/deep-equal-1.0.1.tgz"
},
...,
}
}
}
npm publish .
in your project directory.
$ npm publish .
This talk should get you from 0 to publishing your own command line application in Node.js
We're hiring!
?