FAQ
I'm wondering what are some common ways to approach the problem of figuring
out which arguments the user has passed to a function.

It's a problem I've encountered many times when writing libraries with
APIs; especially for functions with optional arguments.
Each such function requires logic to figure out which of the arguments were
supplied, and assign default values to those which weren't.
A function with just a few arguments requires a large chunk of code just
for this purpose.

An alternative approach is to use an `options` object, the fields of which
represent the arguments, and directly assigned by the user.
This, however, imo, is less suitable for public APIs. I prefer to have
function signatures with distinct arguments.

It seemed to me like there should be a programmatic solution to this. Each
function's arguments should hold certain conditions. Arguments must be of
certain types, some are optionals, some have default values, etc.
This led me to develop a module which allows to declare the properties of
the function's arguments. The module resolves tnd disambiguates the
arguments passed by the user based on those declarations.

https://github.com/EyalAr/Decree

Decree works by analyzing a list of argument declarations. It then figures
out all the possible combinations.
For example, a function which receives two arguments, with the first one
optional, has two possible combinations - the user can call the function
with one argument (thus omitting the first one), or with two (thus
providing the first one).
A function with two arguments, of which non is optional, has only one
combination.
When the user calls the function, decree will match the supplied arguments
to a certain combination. If no combination is found, the user supplied
invalid arguments. If more than one combination is found, the user was not
specific enough, and there is ambiguity. Decree can tell where is the
problem.

How do you usually approach this problem?
And what do you think about this solution?

--
Job board: http://jobs.nodejs.org/
New group rules: https://gist.github.com/othiym23/9886289#file-moderation-policy-md
Old group rules: https://github.com/joyent/node/wiki/Mailing-List-Posting-Guidelines
---
You received this message because you are subscribed to the Google Groups "nodejs" group.
To unsubscribe from this group and stop receiving emails from it, send an email to nodejs+unsubscribe@googlegroups.com.
To post to this group, send email to nodejs@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/nodejs/714e2782-1b8b-4203-bcef-36761b65d993%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Search Discussions

  • Tom Boutell at Oct 6, 2014 at 2:47 pm
    It is certainly a legitimate problem, and your solution has elegance going
    for it. My concern would be the performance overhead.

    I do write functions with omittable parameters. But I also tend to limit
    myself to no more than three positional arguments before introducing an
    "options object" that takes the rest, unless performance is at a very
    serious premium (a function called in inner loops thousands of times, for
    instance).

    If I'm allowing omittable parameters, I tend to check arguments.length and
    make decisions on that basis at the top of a function, repopulating the
    named parameters of the function with the values "one parameter over" if
    necessary. In theory this can get complicated, but having many positional
    parameters is too complicated for the end user to remember anyway so I
    would never choose to introduce more than one or two optional parameters in
    the first place.

    (There are cases, again in tight loops, where more than three required,
    positional parameters are unavoidable for performance reasons.)
    On Sunday, October 5, 2014 1:25:14 PM UTC-4, Eyal Arubas wrote:

    I'm wondering what are some common ways to approach the problem of
    figuring out which arguments the user has passed to a function.

    It's a problem I've encountered many times when writing libraries with
    APIs; especially for functions with optional arguments.
    Each such function requires logic to figure out which of the arguments
    were supplied, and assign default values to those which weren't.
    A function with just a few arguments requires a large chunk of code just
    for this purpose.

    An alternative approach is to use an `options` object, the fields of which
    represent the arguments, and directly assigned by the user.
    This, however, imo, is less suitable for public APIs. I prefer to have
    function signatures with distinct arguments.

    It seemed to me like there should be a programmatic solution to this. Each
    function's arguments should hold certain conditions. Arguments must be of
    certain types, some are optionals, some have default values, etc.
    This led me to develop a module which allows to declare the properties of
    the function's arguments. The module resolves tnd disambiguates the
    arguments passed by the user based on those declarations.

    https://github.com/EyalAr/Decree

    Decree works by analyzing a list of argument declarations. It then figures
    out all the possible combinations.
    For example, a function which receives two arguments, with the first one
    optional, has two possible combinations - the user can call the function
    with one argument (thus omitting the first one), or with two (thus
    providing the first one).
    A function with two arguments, of which non is optional, has only one
    combination.
    When the user calls the function, decree will match the supplied arguments
    to a certain combination. If no combination is found, the user supplied
    invalid arguments. If more than one combination is found, the user was not
    specific enough, and there is ambiguity. Decree can tell where is the
    problem.

    How do you usually approach this problem?
    And what do you think about this solution?
    --
    Job board: http://jobs.nodejs.org/
    New group rules: https://gist.github.com/othiym23/9886289#file-moderation-policy-md
    Old group rules: https://github.com/joyent/node/wiki/Mailing-List-Posting-Guidelines
    ---
    You received this message because you are subscribed to the Google Groups "nodejs" group.
    To unsubscribe from this group and stop receiving emails from it, send an email to nodejs+unsubscribe@googlegroups.com.
    To post to this group, send email to nodejs@googlegroups.com.
    To view this discussion on the web visit https://groups.google.com/d/msgid/nodejs/55d11b56-4543-4e39-ba77-fe50d179e8bb%40googlegroups.com.
    For more options, visit https://groups.google.com/d/optout.
  • Eyal Arubas at Oct 6, 2014 at 6:20 pm
    Tom,

    Performance is indeed a concern.
    For each declaration of arguments a function is built by the module (one
    time). This function is called every time we need to determine the
    arguments the user passed. Part of the operation of this function is to try
    to match the user's arguments to some valid combination of arguments. This
    can be more costly than the regular `if-else` boilerplate code.

    I haven't done any benchmarks yet, so I can't say what's the impact on
    performance, if any.

    I agree that more than three optional arguments is not very common, but
    it's not very rare in my experience.
    With 3 optional arguments, the regular boilerplate code of `if-else`
    statements and `arg2 = arg2 || arg1` is a nuisance, but manageable. With 4,
    it's a real headache.
    It's grunt work, and as such, I wanted a way to automate it and make it
    simpler for the programmer to focus on writing the function itself; as well
    as for others reading the code.

    I also agree that it's better not to give the user the option to omit too
    many arguments, but that's a design issue and sometimes unavoidable.

    Thanks for the feedback,
    Eyal.
    On Monday, October 6, 2014 4:20:18 PM UTC+3, Tom Boutell wrote:

    It is certainly a legitimate problem, and your solution has elegance going
    for it. My concern would be the performance overhead.

    I do write functions with omittable parameters. But I also tend to limit
    myself to no more than three positional arguments before introducing an
    "options object" that takes the rest, unless performance is at a very
    serious premium (a function called in inner loops thousands of times, for
    instance).

    If I'm allowing omittable parameters, I tend to check arguments.length and
    make decisions on that basis at the top of a function, repopulating the
    named parameters of the function with the values "one parameter over" if
    necessary. In theory this can get complicated, but having many positional
    parameters is too complicated for the end user to remember anyway so I
    would never choose to introduce more than one or two optional parameters in
    the first place.

    (There are cases, again in tight loops, where more than three required,
    positional parameters are unavoidable for performance reasons.)
    On Sunday, October 5, 2014 1:25:14 PM UTC-4, Eyal Arubas wrote:

    I'm wondering what are some common ways to approach the problem of
    figuring out which arguments the user has passed to a function.

    It's a problem I've encountered many times when writing libraries with
    APIs; especially for functions with optional arguments.
    Each such function requires logic to figure out which of the arguments
    were supplied, and assign default values to those which weren't.
    A function with just a few arguments requires a large chunk of code just
    for this purpose.

    An alternative approach is to use an `options` object, the fields of
    which represent the arguments, and directly assigned by the user.
    This, however, imo, is less suitable for public APIs. I prefer to have
    function signatures with distinct arguments.

    It seemed to me like there should be a programmatic solution to this.
    Each function's arguments should hold certain conditions. Arguments must be
    of certain types, some are optionals, some have default values, etc.
    This led me to develop a module which allows to declare the properties of
    the function's arguments. The module resolves tnd disambiguates the
    arguments passed by the user based on those declarations.

    https://github.com/EyalAr/Decree

    Decree works by analyzing a list of argument declarations. It then
    figures out all the possible combinations.
    For example, a function which receives two arguments, with the first one
    optional, has two possible combinations - the user can call the function
    with one argument (thus omitting the first one), or with two (thus
    providing the first one).
    A function with two arguments, of which non is optional, has only one
    combination.
    When the user calls the function, decree will match the supplied
    arguments to a certain combination. If no combination is found, the user
    supplied invalid arguments. If more than one combination is found, the user
    was not specific enough, and there is ambiguity. Decree can tell where is
    the problem.

    How do you usually approach this problem?
    And what do you think about this solution?
    --
    Job board: http://jobs.nodejs.org/
    New group rules: https://gist.github.com/othiym23/9886289#file-moderation-policy-md
    Old group rules: https://github.com/joyent/node/wiki/Mailing-List-Posting-Guidelines
    ---
    You received this message because you are subscribed to the Google Groups "nodejs" group.
    To unsubscribe from this group and stop receiving emails from it, send an email to nodejs+unsubscribe@googlegroups.com.
    To post to this group, send email to nodejs@googlegroups.com.
    To view this discussion on the web visit https://groups.google.com/d/msgid/nodejs/26e3ff04-0931-4636-b3f5-4d8e4ec03d4a%40googlegroups.com.
    For more options, visit https://groups.google.com/d/optout.
  • Adrian Lynch at Oct 6, 2014 at 2:47 pm
    I like the idea. Have you used it in anger yet? How did it feel in a bigger
    code base? Did it get in the way or hinder your dev?

    We're having the same debate on a new app we're developing and we can't
    settle on an answer.

    Looking forward to more perspective on this...

    Adrian
    On 5 October 2014 18:25, Eyal Arubas wrote:

    I'm wondering what are some common ways to approach the problem of
    figuring out which arguments the user has passed to a function.

    It's a problem I've encountered many times when writing libraries with
    APIs; especially for functions with optional arguments.
    Each such function requires logic to figure out which of the arguments
    were supplied, and assign default values to those which weren't.
    A function with just a few arguments requires a large chunk of code just
    for this purpose.

    An alternative approach is to use an `options` object, the fields of which
    represent the arguments, and directly assigned by the user.
    This, however, imo, is less suitable for public APIs. I prefer to have
    function signatures with distinct arguments.

    It seemed to me like there should be a programmatic solution to this. Each
    function's arguments should hold certain conditions. Arguments must be of
    certain types, some are optionals, some have default values, etc.
    This led me to develop a module which allows to declare the properties of
    the function's arguments. The module resolves tnd disambiguates the
    arguments passed by the user based on those declarations.

    https://github.com/EyalAr/Decree

    Decree works by analyzing a list of argument declarations. It then figures
    out all the possible combinations.
    For example, a function which receives two arguments, with the first one
    optional, has two possible combinations - the user can call the function
    with one argument (thus omitting the first one), or with two (thus
    providing the first one).
    A function with two arguments, of which non is optional, has only one
    combination.
    When the user calls the function, decree will match the supplied arguments
    to a certain combination. If no combination is found, the user supplied
    invalid arguments. If more than one combination is found, the user was not
    specific enough, and there is ambiguity. Decree can tell where is the
    problem.

    How do you usually approach this problem?
    And what do you think about this solution?

    --
    Job board: http://jobs.nodejs.org/
    New group rules:
    https://gist.github.com/othiym23/9886289#file-moderation-policy-md
    Old group rules:
    https://github.com/joyent/node/wiki/Mailing-List-Posting-Guidelines
    ---
    You received this message because you are subscribed to the Google Groups
    "nodejs" group.
    To unsubscribe from this group and stop receiving emails from it, send an
    email to nodejs+unsubscribe@googlegroups.com.
    To post to this group, send email to nodejs@googlegroups.com.
    To view this discussion on the web visit
    https://groups.google.com/d/msgid/nodejs/714e2782-1b8b-4203-bcef-36761b65d993%40googlegroups.com
    <https://groups.google.com/d/msgid/nodejs/714e2782-1b8b-4203-bcef-36761b65d993%40googlegroups.com?utm_medium=email&utm_source=footer>
    .
    For more options, visit https://groups.google.com/d/optout.
    --
    Job board: http://jobs.nodejs.org/
    New group rules: https://gist.github.com/othiym23/9886289#file-moderation-policy-md
    Old group rules: https://github.com/joyent/node/wiki/Mailing-List-Posting-Guidelines
    ---
    You received this message because you are subscribed to the Google Groups "nodejs" group.
    To unsubscribe from this group and stop receiving emails from it, send an email to nodejs+unsubscribe@googlegroups.com.
    To post to this group, send email to nodejs@googlegroups.com.
    To view this discussion on the web visit https://groups.google.com/d/msgid/nodejs/CAH368SQBm9SFJEDutQSZMkXTLkzBn%3DvtJXTCvK8q0kOZOm7yBg%40mail.gmail.com.
    For more options, visit https://groups.google.com/d/optout.
  • Jimb Esser at Oct 6, 2014 at 6:20 pm
    At Cloud Party, we decided to avoid the ambiguity of having optional
    arguments omitted, and instead took the approach used in other languages
    where you just explicitly pass null or undefined for the optional
    arguments. This had the readability advantage of, given a function
    signature and a call, you knew exactly which parameter was for which
    argument without having to know anything about which are optional and which
    are expected to be which type and what the types are in the caller. It
    also allows for slightly stricter code verification (e.g. generate a linter
    error if any call for a known function is missing an argument).
      Refactoring was slightly more work, as you had to actually touch every
    line of code that called a function when you added a new optional argument
    - on the other hand, when refactoring Javascript, we've found that it's
    generally pretty critical to actually inspect every line of code calling
    your function, so that was not much of a downside.

    We also followed a similar rule as stated earlier in the thread - after a
    function took more than 3-5 arguments, for both readability and
    maintainability, change it to take an options object instead (or, in a lot
    of cases where it makes sense, 1 required parameter, an optional options
    object, and a callback). Though, more recently, when I'm writing a new
    function signature, I generally ask myself: "Might I want to add more
    optional flags/arguments in the future? If so, might as well just make it
    take an options argument now".

    Though, in performance critical code (if your app has any) performance
    trumps all other rules, of course =).
    On Monday, October 6, 2014 7:47:48 AM UTC-7, Adrian Lynch wrote:

    I like the idea. Have you used it in anger yet? How did it feel in a
    bigger code base? Did it get in the way or hinder your dev?

    We're having the same debate on a new app we're developing and we can't
    settle on an answer.

    Looking forward to more perspective on this...

    Adrian

    On 5 October 2014 18:25, Eyal Arubas <eyala...@gmail.com <javascript:>>
    wrote:
    I'm wondering what are some common ways to approach the problem of
    figuring out which arguments the user has passed to a function.

    It's a problem I've encountered many times when writing libraries with
    APIs; especially for functions with optional arguments.
    Each such function requires logic to figure out which of the arguments
    were supplied, and assign default values to those which weren't.
    A function with just a few arguments requires a large chunk of code just
    for this purpose.

    An alternative approach is to use an `options` object, the fields of
    which represent the arguments, and directly assigned by the user.
    This, however, imo, is less suitable for public APIs. I prefer to have
    function signatures with distinct arguments.

    It seemed to me like there should be a programmatic solution to this.
    Each function's arguments should hold certain conditions. Arguments must be
    of certain types, some are optionals, some have default values, etc.
    This led me to develop a module which allows to declare the properties of
    the function's arguments. The module resolves tnd disambiguates the
    arguments passed by the user based on those declarations.

    https://github.com/EyalAr/Decree

    Decree works by analyzing a list of argument declarations. It then
    figures out all the possible combinations.
    For example, a function which receives two arguments, with the first one
    optional, has two possible combinations - the user can call the function
    with one argument (thus omitting the first one), or with two (thus
    providing the first one).
    A function with two arguments, of which non is optional, has only one
    combination.
    When the user calls the function, decree will match the supplied
    arguments to a certain combination. If no combination is found, the user
    supplied invalid arguments. If more than one combination is found, the user
    was not specific enough, and there is ambiguity. Decree can tell where is
    the problem.

    How do you usually approach this problem?
    And what do you think about this solution?

    --
    Job board: http://jobs.nodejs.org/
    New group rules:
    https://gist.github.com/othiym23/9886289#file-moderation-policy-md
    Old group rules:
    https://github.com/joyent/node/wiki/Mailing-List-Posting-Guidelines
    ---
    You received this message because you are subscribed to the Google Groups
    "nodejs" group.
    To unsubscribe from this group and stop receiving emails from it, send an
    email to nodejs+un...@googlegroups.com <javascript:>.
    To post to this group, send email to nod...@googlegroups.com
    <javascript:>.
    To view this discussion on the web visit
    https://groups.google.com/d/msgid/nodejs/714e2782-1b8b-4203-bcef-36761b65d993%40googlegroups.com
    <https://groups.google.com/d/msgid/nodejs/714e2782-1b8b-4203-bcef-36761b65d993%40googlegroups.com?utm_medium=email&utm_source=footer>
    .
    For more options, visit https://groups.google.com/d/optout.
    --
    Job board: http://jobs.nodejs.org/
    New group rules: https://gist.github.com/othiym23/9886289#file-moderation-policy-md
    Old group rules: https://github.com/joyent/node/wiki/Mailing-List-Posting-Guidelines
    ---
    You received this message because you are subscribed to the Google Groups "nodejs" group.
    To unsubscribe from this group and stop receiving emails from it, send an email to nodejs+unsubscribe@googlegroups.com.
    To post to this group, send email to nodejs@googlegroups.com.
    To view this discussion on the web visit https://groups.google.com/d/msgid/nodejs/ab4b9551-67e4-46c4-9803-403f6113c9f0%40googlegroups.com.
    For more options, visit https://groups.google.com/d/optout.
  • Eyal Arubas at Oct 7, 2014 at 7:47 am
    Jimb,

    I like the idea of having a convention of assigning null / undefined
    instead of omitting arguments. Refactoring may indeed take more time, but
    as you implied - it also means more discipline and higher code quality.
    However, you can't always educate your users. Your method works great for
    APIs for which you know who are the users; but with public libraries and
    modules, your users are most likely not used to those conventions.

    Thanks for sharing,
    Eyal.

    On Tuesday, October 7, 2014 2:06:05 AM UTC+8, Jimb Esser wrote:

    At Cloud Party, we decided to avoid the ambiguity of having optional
    arguments omitted, and instead took the approach used in other languages
    where you just explicitly pass null or undefined for the optional
    arguments. This had the readability advantage of, given a function
    signature and a call, you knew exactly which parameter was for which
    argument without having to know anything about which are optional and which
    are expected to be which type and what the types are in the caller. It
    also allows for slightly stricter code verification (e.g. generate a linter
    error if any call for a known function is missing an argument).
    Refactoring was slightly more work, as you had to actually touch every
    line of code that called a function when you added a new optional argument
    - on the other hand, when refactoring Javascript, we've found that it's
    generally pretty critical to actually inspect every line of code calling
    your function, so that was not much of a downside.

    We also followed a similar rule as stated earlier in the thread - after a
    function took more than 3-5 arguments, for both readability and
    maintainability, change it to take an options object instead (or, in a lot
    of cases where it makes sense, 1 required parameter, an optional options
    object, and a callback). Though, more recently, when I'm writing a new
    function signature, I generally ask myself: "Might I want to add more
    optional flags/arguments in the future? If so, might as well just make it
    take an options argument now".

    Though, in performance critical code (if your app has any) performance
    trumps all other rules, of course =).
    On Monday, October 6, 2014 7:47:48 AM UTC-7, Adrian Lynch wrote:

    I like the idea. Have you used it in anger yet? How did it feel in a
    bigger code base? Did it get in the way or hinder your dev?

    We're having the same debate on a new app we're developing and we can't
    settle on an answer.

    Looking forward to more perspective on this...

    Adrian
    On 5 October 2014 18:25, Eyal Arubas wrote:

    I'm wondering what are some common ways to approach the problem of
    figuring out which arguments the user has passed to a function.

    It's a problem I've encountered many times when writing libraries with
    APIs; especially for functions with optional arguments.
    Each such function requires logic to figure out which of the arguments
    were supplied, and assign default values to those which weren't.
    A function with just a few arguments requires a large chunk of code just
    for this purpose.

    An alternative approach is to use an `options` object, the fields of
    which represent the arguments, and directly assigned by the user.
    This, however, imo, is less suitable for public APIs. I prefer to have
    function signatures with distinct arguments.

    It seemed to me like there should be a programmatic solution to this.
    Each function's arguments should hold certain conditions. Arguments must be
    of certain types, some are optionals, some have default values, etc.
    This led me to develop a module which allows to declare the properties
    of the function's arguments. The module resolves tnd disambiguates the
    arguments passed by the user based on those declarations.

    https://github.com/EyalAr/Decree

    Decree works by analyzing a list of argument declarations. It then
    figures out all the possible combinations.
    For example, a function which receives two arguments, with the first one
    optional, has two possible combinations - the user can call the function
    with one argument (thus omitting the first one), or with two (thus
    providing the first one).
    A function with two arguments, of which non is optional, has only one
    combination.
    When the user calls the function, decree will match the supplied
    arguments to a certain combination. If no combination is found, the user
    supplied invalid arguments. If more than one combination is found, the user
    was not specific enough, and there is ambiguity. Decree can tell where is
    the problem.

    How do you usually approach this problem?
    And what do you think about this solution?

    --
    Job board: http://jobs.nodejs.org/
    New group rules:
    https://gist.github.com/othiym23/9886289#file-moderation-policy-md
    Old group rules:
    https://github.com/joyent/node/wiki/Mailing-List-Posting-Guidelines
    ---
    You received this message because you are subscribed to the Google
    Groups "nodejs" group.
    To unsubscribe from this group and stop receiving emails from it, send
    an email to nodejs+un...@googlegroups.com.
    To post to this group, send email to nod...@googlegroups.com.
    To view this discussion on the web visit
    https://groups.google.com/d/msgid/nodejs/714e2782-1b8b-4203-bcef-36761b65d993%40googlegroups.com
    <https://groups.google.com/d/msgid/nodejs/714e2782-1b8b-4203-bcef-36761b65d993%40googlegroups.com?utm_medium=email&utm_source=footer>
    .
    For more options, visit https://groups.google.com/d/optout.
    --
    Job board: http://jobs.nodejs.org/
    New group rules: https://gist.github.com/othiym23/9886289#file-moderation-policy-md
    Old group rules: https://github.com/joyent/node/wiki/Mailing-List-Posting-Guidelines
    ---
    You received this message because you are subscribed to the Google Groups "nodejs" group.
    To unsubscribe from this group and stop receiving emails from it, send an email to nodejs+unsubscribe@googlegroups.com.
    To post to this group, send email to nodejs@googlegroups.com.
    To view this discussion on the web visit https://groups.google.com/d/msgid/nodejs/be99def3-b1d9-4fdf-a200-fa8ab4e9584d%40googlegroups.com.
    For more options, visit https://groups.google.com/d/optout.
  • Eyal Arubas at Oct 6, 2014 at 6:28 pm
    Adrian,

    My main motivation for writing this module is another module I'm working
    on; in which I have lot's of API functions which take optional arguments.
    I use Decree extensively in that module (you may want to take a look here
    <https://github.com/EyalAr/lwip>).
    Before using Decree, my functions were simply too big and cumbersome. When
    reading the code of a function, by the time you got to the real meat, you
    had to read 10-20 lines of irrelevant code.
    As I wrote to Tom above, I imagine there is some performance hit, but I
    haven't checked yet. I am sure, though, that by making your functions
    smaller and more focused, they are easier to maintain and debug.

    Thanks for the interest,
    Eyal.

    I should note that both Decree and the other module I mentioned are in beta
    and have not been used in production. But they are heavily tested.
    On Monday, October 6, 2014 5:47:48 PM UTC+3, Adrian Lynch wrote:

    I like the idea. Have you used it in anger yet? How did it feel in a
    bigger code base? Did it get in the way or hinder your dev?

    We're having the same debate on a new app we're developing and we can't
    settle on an answer.

    Looking forward to more perspective on this...

    Adrian

    On 5 October 2014 18:25, Eyal Arubas <eyala...@gmail.com <javascript:>>
    wrote:
    I'm wondering what are some common ways to approach the problem of
    figuring out which arguments the user has passed to a function.

    It's a problem I've encountered many times when writing libraries with
    APIs; especially for functions with optional arguments.
    Each such function requires logic to figure out which of the arguments
    were supplied, and assign default values to those which weren't.
    A function with just a few arguments requires a large chunk of code just
    for this purpose.

    An alternative approach is to use an `options` object, the fields of
    which represent the arguments, and directly assigned by the user.
    This, however, imo, is less suitable for public APIs. I prefer to have
    function signatures with distinct arguments.

    It seemed to me like there should be a programmatic solution to this.
    Each function's arguments should hold certain conditions. Arguments must be
    of certain types, some are optionals, some have default values, etc.
    This led me to develop a module which allows to declare the properties of
    the function's arguments. The module resolves tnd disambiguates the
    arguments passed by the user based on those declarations.

    https://github.com/EyalAr/Decree

    Decree works by analyzing a list of argument declarations. It then
    figures out all the possible combinations.
    For example, a function which receives two arguments, with the first one
    optional, has two possible combinations - the user can call the function
    with one argument (thus omitting the first one), or with two (thus
    providing the first one).
    A function with two arguments, of which non is optional, has only one
    combination.
    When the user calls the function, decree will match the supplied
    arguments to a certain combination. If no combination is found, the user
    supplied invalid arguments. If more than one combination is found, the user
    was not specific enough, and there is ambiguity. Decree can tell where is
    the problem.

    How do you usually approach this problem?
    And what do you think about this solution?

    --
    Job board: http://jobs.nodejs.org/
    New group rules:
    https://gist.github.com/othiym23/9886289#file-moderation-policy-md
    Old group rules:
    https://github.com/joyent/node/wiki/Mailing-List-Posting-Guidelines
    ---
    You received this message because you are subscribed to the Google Groups
    "nodejs" group.
    To unsubscribe from this group and stop receiving emails from it, send an
    email to nodejs+un...@googlegroups.com <javascript:>.
    To post to this group, send email to nod...@googlegroups.com
    <javascript:>.
    To view this discussion on the web visit
    https://groups.google.com/d/msgid/nodejs/714e2782-1b8b-4203-bcef-36761b65d993%40googlegroups.com
    <https://groups.google.com/d/msgid/nodejs/714e2782-1b8b-4203-bcef-36761b65d993%40googlegroups.com?utm_medium=email&utm_source=footer>
    .
    For more options, visit https://groups.google.com/d/optout.
    --
    Job board: http://jobs.nodejs.org/
    New group rules: https://gist.github.com/othiym23/9886289#file-moderation-policy-md
    Old group rules: https://github.com/joyent/node/wiki/Mailing-List-Posting-Guidelines
    ---
    You received this message because you are subscribed to the Google Groups "nodejs" group.
    To unsubscribe from this group and stop receiving emails from it, send an email to nodejs+unsubscribe@googlegroups.com.
    To post to this group, send email to nodejs@googlegroups.com.
    To view this discussion on the web visit https://groups.google.com/d/msgid/nodejs/89ee28ed-15f1-4281-97b5-64055870d2cb%40googlegroups.com.
    For more options, visit https://groups.google.com/d/optout.
  • Axel Kittenberger at Oct 6, 2014 at 7:20 pm
    I agree about the motivation.

    Its not even only ambigious and optional argument lists, its even longer
    argument lists that make a problem, since its often not clear to the callee
    which argument means what. I never get it, why the order of arguments its
    considered to be the only argument structuring mechanism to function calls
    so many languages offer.

    Or argument lists that are changing in development or library releases.
    That can be a pain to get them all correct again.

    I know, most people will say, just create an object literal and give that
    to the function. Albeit this okayish for the occasional function, and more
    and more standard API functions are adapting to this style or arguments I
    don't like the idea of creating an object just for a single function call.
    I know garbage collectors have become awesome, but it still seems
    unnecessary waste to me, especially if that function is that 10% of code
    that called often enough to be 90% of runtime already anyway.

    What I'm doing now is creating functions that take arguments with
    alternating string specifier and parameter value.

    like: makeCoffee( 'sugars', 7, 'flavor', 'bitter', 'size', 4 );

    I call it "free strings" method.

    In code I write it like this:

    makeCoffee(
       'sugars', 7,
       'flavor', 'bitter',
       'size', 4
    );

    At first I would simple code makeCoffee like this:

    function makeCoffee( /* free strings */ )
    {
       var
         sugars = 3, // defaultValue
         flavor = 'sweet',
         size = 2;

       for( var a = 0, aZ = arguments.length; a < aZ; a+=2 )
       {
           switch( arguments[ a ] )
           {
           case 'sugars' :
              // bla
              break;
            ..etc..
          }
       }

       // actual function block
    };

    As its true it gets repetitive with not much expressiveness (albeit I
    believe quite good in runtime), I then tried to code some generic
    meta-handlers, like you did, but never was satisfied with the result. Again
    it often resulted in creation of several ultra-short-lived objects on the
    fly for each function call.

    Right now I'm using a code generator to create these repetitive code blocks
    like aboth. However, its developing while I'm using it and yet not in a
    state near to be released except eating my own dog food.

    To sum it up: I get the problem. I agree it is one. Actually ii is an issue
    with javascript which it actually shares with most other dynamic languages.
    Albeit not all! R for example has named arguments. There this whole thing
    is nicely handled by the language itself -- as far I got it, never coded
    much beside some "hello world"s in it. I believe a good solution -- next to
    get ECMA to realize this and alter javascript itself to get named arguments
    inkl. default values -- would be a meta language to javascript (similar in
    working than coffeescript) that handles named arguments to compile on the
    fly to javascript. Like with every metalanguage there comes the issue with
    debugging, albeit this can be handled nowadays with source maps.

    Or just accept and create lots of short lived object literals. Or improve
    the Javascript runtime so much that a case can be done, that creating ultra
    short lived object literals and parsing code for it is just as fast as a
    classical ordered argument list.

    --
    Job board: http://jobs.nodejs.org/
    New group rules: https://gist.github.com/othiym23/9886289#file-moderation-policy-md
    Old group rules: https://github.com/joyent/node/wiki/Mailing-List-Posting-Guidelines
    ---
    You received this message because you are subscribed to the Google Groups "nodejs" group.
    To unsubscribe from this group and stop receiving emails from it, send an email to nodejs+unsubscribe@googlegroups.com.
    To post to this group, send email to nodejs@googlegroups.com.
    To view this discussion on the web visit https://groups.google.com/d/msgid/nodejs/CABg07ftmorn1BEE8dOYsNOvEiYL0VWkDMBSMHPeGbVYFxVX%2BGg%40mail.gmail.com.
    For more options, visit https://groups.google.com/d/optout.
  • Eyal Arubas at Oct 7, 2014 at 7:47 am
    Axel,

    Your solution pretty much brings named arguments into Javascript. Pretty
    cool. First time I'm seeing this approach.

    I think that in most other languages which don't have named arguments,
    users are not allowed to carelessly omit arguments. And if they do, they
    will encounter a compilation / runtime error before the function even
    starts to run.
    In JS we have the additional burden of validating functions' input. It's a
    sort of an additional defensive programming we have to do.
    Some say, btw, that as long as the docs state how to use the function, it's
    the user's responsibility to use it correctly.

    In JS users are used to calling functions by simply passing the arguments
    they want. And knowing that the function will just throw an exception if
    they misused it (a.k.a. "programmer error"). In this context, it might be
    worth reading this article
    <https://www.joyent.com/developers/node/design/errors>.
    As I mentioned before, any approach which does not follow the regular
    function-calling paradigm, will have to re-educate the users how to use the
    functions; which is not easy.
    For APIs for which it's known who are the users, it's definitely possible
    (internal / private libraries). But for public libraries I think we don't
    always have the luxury of changing our users' habits.

    About your solution - I think it's a nice approach. You said you are
    concerned with creating new objects at runtime due to performance. But any
    non-trivial solution will incur a performance hit. It should be interesting
    to do some benchmarks.

    Eyal.
    On Tuesday, October 7, 2014 3:21:25 AM UTC+8, Axel Kittenberger wrote:

    I agree about the motivation.

    Its not even only ambigious and optional argument lists, its even longer
    argument lists that make a problem, since its often not clear to the callee
    which argument means what. I never get it, why the order of arguments its
    considered to be the only argument structuring mechanism to function calls
    so many languages offer.

    Or argument lists that are changing in development or library releases.
    That can be a pain to get them all correct again.

    I know, most people will say, just create an object literal and give that
    to the function. Albeit this okayish for the occasional function, and more
    and more standard API functions are adapting to this style or arguments I
    don't like the idea of creating an object just for a single function call.
    I know garbage collectors have become awesome, but it still seems
    unnecessary waste to me, especially if that function is that 10% of code
    that called often enough to be 90% of runtime already anyway.

    What I'm doing now is creating functions that take arguments with
    alternating string specifier and parameter value.

    like: makeCoffee( 'sugars', 7, 'flavor', 'bitter', 'size', 4 );

    I call it "free strings" method.

    In code I write it like this:

    makeCoffee(
    'sugars', 7,
    'flavor', 'bitter',
    'size', 4
    );

    At first I would simple code makeCoffee like this:

    function makeCoffee( /* free strings */ )
    {
    var
    sugars = 3, // defaultValue
    flavor = 'sweet',
    size = 2;

    for( var a = 0, aZ = arguments.length; a < aZ; a+=2 )
    {
    switch( arguments[ a ] )
    {
    case 'sugars' :
    // bla
    break;
    ..etc..
    }
    }

    // actual function block
    };

    As its true it gets repetitive with not much expressiveness (albeit I
    believe quite good in runtime), I then tried to code some generic
    meta-handlers, like you did, but never was satisfied with the result. Again
    it often resulted in creation of several ultra-short-lived objects on the
    fly for each function call.

    Right now I'm using a code generator to create these repetitive code
    blocks like aboth. However, its developing while I'm using it and yet not
    in a state near to be released except eating my own dog food.

    To sum it up: I get the problem. I agree it is one. Actually ii is an
    issue with javascript which it actually shares with most other dynamic
    languages. Albeit not all! R for example has named arguments. There this
    whole thing is nicely handled by the language itself -- as far I got it,
    never coded much beside some "hello world"s in it. I believe a good
    solution -- next to get ECMA to realize this and alter javascript itself to
    get named arguments inkl. default values -- would be a meta language to
    javascript (similar in working than coffeescript) that handles named
    arguments to compile on the fly to javascript. Like with every metalanguage
    there comes the issue with debugging, albeit this can be handled nowadays
    with source maps.

    Or just accept and create lots of short lived object literals. Or improve
    the Javascript runtime so much that a case can be done, that creating ultra
    short lived object literals and parsing code for it is just as fast as a
    classical ordered argument list.
    --
    Job board: http://jobs.nodejs.org/
    New group rules: https://gist.github.com/othiym23/9886289#file-moderation-policy-md
    Old group rules: https://github.com/joyent/node/wiki/Mailing-List-Posting-Guidelines
    ---
    You received this message because you are subscribed to the Google Groups "nodejs" group.
    To unsubscribe from this group and stop receiving emails from it, send an email to nodejs+unsubscribe@googlegroups.com.
    To post to this group, send email to nodejs@googlegroups.com.
    To view this discussion on the web visit https://groups.google.com/d/msgid/nodejs/be431b55-d664-469f-af92-b36e1441d7d7%40googlegroups.com.
    For more options, visit https://groups.google.com/d/optout.

Related Discussions

Discussion Navigation
viewthread | post
Discussion Overview
groupnodejs @
categoriesnodejs
postedOct 5, '14 at 5:32p
activeOct 7, '14 at 7:47a
posts9
users5
websitenodejs.org
irc#node.js

People

Translate

site design / logo © 2022 Grokbase