I suspect this is an issue due to the way how Calamari starts the Python process.
One can call python scripts via command line (e.g. using inline PowerShell) as
python $PathToScript. Using the native
Python option I expect the same result. This works fine for simple Python packages in Octopus but not for one special case, the native Python execution does not work:
Create a package with the following content (let’s call it
main.py but the name does not matter here, I could’ve also called it
if __name__ == '__main__':
Python has this convention whereby
__name__ is defined as
__main__ and you will see this works fine when executing
python $PathToScript locally in your shell of choice or in Octopus using inline PowerShell. However, when using the
Script file in package option and pointing it to
main.py, this does not work. Since all other Python files execute fine using this option, I’d consider this a bug. The impact is quite high because there are libraries that require end users to use such a convention, as a result, the only way to use Python from such a package is to call
python $ScriptPath via PowerShell but this completely defeats the point of the native Octopus integration and we do not get live streaming of stdout/stderr, etc.
I am using Octopus
2019.6.7 (LTS) and Calamari
Thanks for getting in touch! I’ll start by saying, I’m not a python expert.
What I can explain is how we invoke your python scripts. We use
runpy.run_path to execute your python script. We do this so we can deliver Octopus Variables into your script file.
Here is the documentation on
runpy which mentions these global variables: https://docs.python.org/3/library/runpy.html
And here is the code we use to bootstrap and execute your python script: https://github.com/OctopusDeploy/Calamari/blob/master/source/Calamari.Shared/Integration/Scripting/Python/PythonBootstrapper.cs
Hopefully that gives you enough context to help me understand whether:
- You can execute your scripts in a slightly different way
- We can offer some kind of enhancement to enable your scripts to “just work” within an Octopus world
- There is some kind of compromise between these options
Hope that helps!
@Michael_Noonan Thanks for the detailed info and the link to
runpy and the source code where I could see that I calls
runpy.run_path with only 1 argument. With that I could create a simple test script to reproduce and experiment:
from runpy import run_path
As per documentation of
runpy the value of
<run_path> in this case and not
__main__. I could confirm this by adapting the test package, which works now:
if __name__ == '<run_path>':
However, I’d still expect some issues later down the road as I suspect some other 3rd party Python packages have the
if __name__ == '__main__' convention hard-coded in them. It would be great if Octopus had a link to
runpy in its docs. It might be useful to optionally call
run_path with 3 arguments (maybe a configuration option in the Octopus task) and pass the value of
run_name. For the moment, I cannot say yet this will cause an issue further down the road for us but it’s something you guys might want to discuss internally.
This topic was automatically closed 30 days after the last reply. New replies are no longer allowed.