pyinvoke / invoke

Pythonic task management & command execution.
http://pyinvoke.org
BSD 2-Clause "Simplified" License
4.41k stars 368 forks source link

Custom core parser arguments are not available in Config #632

Open JamesRamm opened 5 years ago

JamesRamm commented 5 years ago

When following the instructions (http://docs.pyinvoke.org/en/1.2/concepts/library.html#modifying-core-parser-arguments) to modify the core parser arguments, I cannot access any such arguments from a 'task'.

E.g., my custom program class:

class Swa(Fab):
   def core_args(self):
      core_args = super(Swa, self).core_args()
      extra_args = [
         Argument(
            names=("m", "myarg"),
            help="A custom argument"
         ),
      ]
      return core_args + extra_args

program = Swa(namespace=ns, name="SWA", version="1.0.0", executor_class=Executor, config_class=Config)

In my task, I would expect that myarg is available somewhere in the Config (probably in the run section). It is not.... It seems custom core args are only available within the Program class then, which is not particularly useful.

My thoughts are that the update_config method should be changed to add 'unknown' arguments to the Config dict.

kumekay commented 5 years ago

I've experienced same problem right today, in my own Program class I just extended update_config with args

lass MyProgram(Program):
        def core_args(self):
            core_args =  super(MyProgram, self).core_args())

            extra_args = [
                    Argument(names=('foo', 'F'), help="Foo", default='bar'),
            ]

            return core_args + extra_args

        def update_config(self, merge=True):
            # Add core args to config:
            self.config["args"] = self.args

            return super(MyProgram, self).update_config(merge=merge)
hed854 commented 4 years ago

This is now working (tested on invoke 1.4)

class BuildTools(Program):
    def core_args(self):
        core_args = super(BuildTools, self).core_args()
        extra_args = [
            Argument(name=("project"), help="Project name")
        ]
        return core_args + extra_args

    def update_config(self):
        self.config["args"] = self.args
        super().update_config(merge=True)

@task()
def build(c):
    # all args in config
    for i in c['args']:
        print(i)

    # get custom arg value
    print(c.args.project.value)

You'll see your project custom core_arg merged in the config and usable from any task!