
Security News
Crates.io Implements Trusted Publishing Support
Crates.io adds Trusted Publishing support, enabling secure GitHub Actions-based crate releases without long-lived API tokens.
machine-as-script
Advanced tools
Build a modified version of a machine that proxies its inputs from CLI arguments and/or --
opts.
$ npm install machine-as-script --save
#!/usr/bin/env node
var asScript = require('machine-as-script');
var MPMath = require('machinepack-math');
asScript({
machine: MPMath.add
}).exec({
success: function (sum){
console.log('Got result:', sum);
}
});
Now you can run your machine as a script and provide inputs as CLI opts:
$ node ./add-numbers.js --a=4 --b=5
# Got result: 9
Note that the machine definition you provide here doesn't have to come from an already-published machinepack-- it can be required locally from your project, or declared inline.
In addition to specifying inputs as --
CLI opts, you can configure your script to accept serial CLI arguments.
Just specify args
as an array of input names, in the expected order:
asScript({
machine: MPMath.add,
args: ['a', 'b']
}).exec({
success: function (sum){
console.log('Got result:', sum);
}
});
Now you can use serial CLI arguments to configure the related inputs:
$ node ./add-numbers.js 4 5
# Got result: 9
args
inputIf you don't already have an input named args
, when using machine-as-action, your machine's fn
will receive an array of serial command-line arguments in inputs.args
. THIS IS AN EXPERIMENTAL FEATURE AND COULD CHANGE AT ANY TIME WITHOUT BACKWARDS COMPATIBILITY!!
Sometimes (particularly in a production setting, like on Heroku) you want to be able to use your machine as a script without specifying command-line arguments or checking in credentials or other configuration details to source control. This is typically accomplished using environment variables.
When using machine-as-script
, as an alternative to CLI opts, you can specify input values
using environment variables:
$ ___a=4 ___b=5 node ./add-numbers.js
# Got result: 9
Environment variables work exactly like CLI opts, with the same escaping rules for specifying JSON arrays and dictionaries.
It's usually a good idea to namespace the environment variables specific to your application. Especially since many inputs have fairly common names (as they should!), it's helpful to use a prefix to avoid conflicts with env variables used by other processes.
The default namespace is 3 underscores (___
). In other words, if your machine has an input foo
, then you could configure that input using the environment variable named ___foo
.
To customize the namespace for your script, just specify an envVarNamespace
:
asScript({
machine: MPMath.add,
envVarNamespace: 'add_numbers__'
}).exec({
success: function (sum){
console.log('Got result:', sum);
}
});
Now your custom string will be the expected namespace for environment variables:
$ add_numbers__a=4 add_numbers__b=5 node ./add-numbers.js
# Got result: 9
Note that input names are case-sensitive, and therefore the names of environment variables understood by this module are also case-sensitive.
On Windows, the names of environment variables are capitalized/case-insensitive, so you may have difficulties using this approach. I'm happy to help in the implementation of a workaround if you need this and have any ideas for how to do it (hit me up on Twitter).
So it's really easy to see how string input values can be configured using CLI opts, arguments, or environment variables. But more often than not, when configuring a script, you need to specify an input value that isn't a string-- things like arrays, dictionaries, booleans, and numbers.
This module lets you configure any input value-- even lamdas. Internally, it uses the parseHuman()
method from rttc
. For a more detailed look at the exact rules, check out the README in the rttc repo. Below, we look at one example for each of the major use cases you're likely to run into.
$ node ./add-numbers.js --a='4' --b='5'
$ node ./divide-numbers.js --a='9' --b='5' --useFloatingPoint='false'
->
) inputs$ node ./each.js --array='[]' --iteratee='function (thing){ return thing.foo; }'
{}
) and array ([]
) inputsIf an input is expecting a dictionary or array (i.e. its example is a dictionary or array), then its value should be specified as JSON.
$ node ./count-keys.js --someDictionary='{"this": {"must": ["be","JSON","encoded"]}}'
$ node ./count-items.js --someArray='["this","must","be","JSON","encoded","too"]'
*
) inputsIf an input is expecting generic JSON (i.e. its example is '*'
), then its value should be specified as JSON-- even if that value is a simple string, number, or boolean.
$ node ./is-null.js --value='{w: true, x: null, y: "some string", z: 34}'
$ node ./is-null.js --value='["should be json encoded", 4, null]'
$ node ./is-null.js --value='"even if it is a string"'
$ node ./is-null.js --value='22353'
$ node ./is-null.js --value='true'
$ node ./is-null.js --value='null'
===
) inputsFor the automatic console output of machine-as-script, mutable reference inputs work just like JSON (*
) inputs. For custom behavior, just override the automatic handling using .exec()
.
To learn more about rttc types, check out the rttc README on GitHub.
The rules for escaping env vars, CLI opts, and CLI arguments can vary across operating systems. However, a good reference point is the escape machine in mp-process. That's what the machinepack
command-line tool uses internally for creating code samples after a machine is run using mp exec
.
It's always best to keep things simple. In keeping with that spirit, you should never intentionally use both environment variables AND CLI opts/args to configure your script. But weird things are unavoidable, and when debugging, it's helpful to know more about the tools you use in case something jumps out.
Starting from the highest precedence, here is a list of how this module prioritizes your input configurations:
./my-script.js bar
)foo=bar ./my-script.js
)./my-script.js --foo='bar'
)In other words, if you specify the same input as a CLI argument AND as an environment variable or CLI opt, the CLI argument will always "win". And if you specify the same input as an environment variable and CLI opt, the environment variable will always win.
MIT © Mike McNeil
FAQs
Run a machine as a command-line script.
The npm package machine-as-script receives a total of 59 weekly downloads. As such, machine-as-script popularity was classified as not popular.
We found that machine-as-script demonstrated a not healthy version release cadence and project activity because the last version was released a year ago. It has 2 open source maintainers collaborating on the project.
Did you know?
Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.
Security News
Crates.io adds Trusted Publishing support, enabling secure GitHub Actions-based crate releases without long-lived API tokens.
Research
/Security News
Undocumented protestware found in 28 npm packages disrupts UI for Russian-language users visiting Russian and Belarusian domains.
Research
/Security News
North Korean threat actors deploy 67 malicious npm packages using the newly discovered XORIndex malware loader.