Skip to content

Better ways to pass arguments #112

heaths opened this Issue Apr 28, 2014 · 5 comments

3 participants

heaths commented Apr 28, 2014

Passing arguments to tasks via a hashtable can be a pain, especially when you have to pass the hashtable as a string to psake.cmd/.bat. Instead, declare a [string[]] parameter with the ParameterAttribute.ValueFromRemainingArguments field set.

Loop through the arguments and assign to a hashtable (keys begin with '-' while their values don't, for example) and then splat the hashtable to the task for use as parameters to the task.

There's a few ways you could do this for a better command line syntax. This would enable passing parameters easily to psake like so:

psake compile -version -ignoresomething

I have been thinking of such a feature, too. It is tempting, yes.

But there is a drawback to be considered. If we use ValueFromRemainingArguments then we sacrifice validation of existing parameter names (buildFile, taskList, framework, etc.). Namely, if we use misspelled names then this is not interpreted as an error anymore. Instead, misspelled parameters all go to the ValueFromRemainingArguments parameter. This may work in many cases, incorrectly, indeed, and mistakes may be discovered much later. The cost may be higher than benefits of simpler command lines.

Is this a reasonable sacrifice? It depends. In most of tools I decided to avoid this feature but there are good cases for it, e.g. simple wrappers, ideally with no own parameters.



Another potential drawback. With ValueFromRemainingArguments scripts should avoid parameter names same as psake parameters, even sub-strings may be ambiguous. Example: a script has a parameter $Frame. How is -Frame in this command interpreted?

psake task1 -Frame 42

It is treated as the parameter Framework of psake, not as the parameter to be passed in the script. Yes, problems can be resolved, parameters renamed or -Parameters @{Frame=42} can be used in such a case, etc. But this is still an extra trap introduced by ValueFromRemainingArguments.

And, as a related effect, introducing any new parameter to psake in the future will be potentially a breaking change because such a parameter may conflict with script parameters used in command lines with ValueFromRemainingArguments approach.

heaths commented Apr 29, 2014

Maybe you could splat all parameters and let the callers sort it out. In a way, it's sort of like what some JSON frameworks do: they sticky everything they don't know about into a property/object bag and split them back out as-is if needed. Cmdlets could always have their own ValueFromRemainingArguments or the psake scripts could filter @PSBoundParameters themselves before passing them to a subordinate cmdlets.


@heaths, as far as the current project maintainer won't be dealing with any PRs that add or change functionality, I hope it is fair to point you to a similar tool which has this feature implemented (using safe dynamic parameters, not unsafe remaining arguments).

It is Invoke-Build, inspired by psake long time ago and being developed in a parallel universe. If simple syntax is essential for you give it a try. If you have questions or issues let's discuss them there.

P.S. Just in case, as it was mentioned in some other discussions before, psake developers are welcome to borrow ideas and code.


what about leveraging a json formatted string and then just parsing as needed inside the tasks?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Something went wrong with that request. Please try again.