Search code examples
pythonpython-3.xdesign-patternssetuptools

A runall command in setup.py


I have created many custom commands by extending the command class in setuptools python library. The commands are like Clean, RunTest (each individual class with their run(self) method). I have now created a RunAll Class which if also sub classing the Command class and needs to call other commands. Let me show some of my code so as to make it more clear.

class Clean(Command):

description = 'Cleans the build'
user_options = []

def initialize_options(self):
    pass

def finalize_options(self):
    pass

def clean(self):
    print("Cleaning")

def run(self):
    self.clean()

There are some more classes like these like Runtests etc. which are of similar format. Now I create a class called as RunAll which runs all these commands (trying to simulate ant all command). So the code is like.

class RunAll(Command):
"""
runs few specific commands mentioned
"""

description = 'Runs specific commands mentioned'
user_options = []

def initialize_options(self):
    pass

def finalize_options(self):
    pass

def run(self):
    # init,clean,version,build,test,dist
    Clean().clean()
    Version().printVersion()
    RunTests().runtests()
    Dist().dist()

Now when I run python setup.py runall I get the following error.

  File "C:\Users\rsareen\AppData\Local\Programs\Python\Python36\lib\site-packages\setuptools\__init__.py", line 129, in setup
return distutils.core.setup(**attrs)
  File "C:\Users\rsareen\AppData\Local\Programs\Python\Python36\lib\distutils\core.py", line 148, in setup
dist.run_commands()
  File "C:\Users\rsareen\AppData\Local\Programs\Python\Python36\lib\distutils\dist.py", line 955, in run_commands
self.run_command(cmd)
  File "C:\Users\rsareen\AppData\Local\Programs\Python\Python36\lib\distutils\dist.py", line 974, in run_command
cmd_obj.run()
  File ".\setup.py", line 58, in run
Clean().clean()
TypeError: __init__() missing 1 required positional argument: 'dist'

Its not able to get the dist parameter in the Command class.

Basically i am not able to instantiate the commands. But when i do python setup.py clean, it runs perfectly.

Is setuptools designed this way and I need to change my design, or there is any other way to do that?


Solution

  • Command classes seems to require a parameter and store that parameter in self.distribution. So pass it to command classes you create:

    Clean(self.distribution).clean()
    …
    

    Or you can run a different command by name using run_command:

    self.run_command('clean')
    …