Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Consider better support for arrays with coercion #50

Closed
nexdrew opened this issue Aug 12, 2016 · 1 comment
Closed

Consider better support for arrays with coercion #50

nexdrew opened this issue Aug 12, 2016 · 1 comment

Comments

@nexdrew
Copy link
Member

nexdrew commented Aug 12, 2016

Problem

Through testing of the coerce option, I noticed that the coercion function is called for each element in the array instead of once for the entire array, regardless of the array option. This makes it impossible to coerce the array-as-a-whole within a coercion function.

Here's an example:

var parse = require('yargs-parser')
var result = parse.detailed(process.argv.slice(2), {
  array: ['add'],
  coerce: {
    add: function (arg) {
      return arg.map(Number).reduce(function (x, y) {
        return x + y
      }, 0)
    }
  }
})
console.log(result)
$ node coerce.js --add 1 2 3
{ argv: { _: [], add: [ '1', '2', '3' ] },
  error: 
   TypeError: arg.map is not a function
       ... snip stack...,
  aliases: { add: [] },
  newAliases: {},
  configuration: 
   { 'short-option-groups': true,
     'camel-case-expansion': true,
     'dot-notation': true,
     'parse-numbers': true,
     'boolean-negation': true } }

Proposal

Defer coercion (at least for arrays) until after initial parsing is done

This would allow the above example to work as is, with the following result:

$ node coerce.js --add 1 2 3
{ argv: { _: [], add: 6 },
  error: null,
  aliases: { add: [] },
  newAliases: {},
  configuration: 
   { 'short-option-groups': true,
     'camel-case-expansion': true,
     'dot-notation': true,
     'parse-numbers': true,
     'boolean-negation': true } }

Note that no context is lost with this approach because the coercion can always iterate over the array of values if it wishes to coerce them individually.

A possible alternative could be to pass the existing value (from argv) to the coerce function as a second parameter, to potentially allow coercion to "build up" or "reduce to" a desired value, but I think this could lead to a lot of confusion and would argue against it.

@bcoe
Copy link
Member

bcoe commented Aug 13, 2016

@nexdrew I like this approach 👍

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants