Troubleshooting your STK and Python integration

Information

 
QuestionHaving Trouble Connecting STK with Python (using Anaconda)?
Answer
Note: An STK Integration license is required to connect to STK with Python.

When trying to connect to STK using Python, and running code such as:
 
import comtypes
from comtypes.client import CreateObject
uiApplication = CreateObject("STK12.Application")
uiApplication.Visible=True
uiApplication.UserControl=True
root=uiApplication.Personality2

You may experience this error:
 
AttributeError: module ‘comtypes.gen.AgUiApplicationLib’ has no attribute ‘_IAgUiApplication’

And may see something similar to this:
PythonError

This error is the result of an improper initialization of the Python wrapper files located in the comtypes gen folder. This article will go through a few different solutions - folder permissions, testing with other Component Object Model (COM) enabled tools, type incompatibility, and brute force – to solve the error. This problem is likely not an STK specific issue, but rather an issue between Python and comtypes.


Folder Permissions

It is helpful to have some background on these issues to best solve the problem at hand. Comtypes needs to do a one-time initialization pass before you can start working with COM items, such as the Object Model in STK. The commands above tell comtypes to build Python wrappers around the Type Library files associated with STK. This is how you get the benefits of Tab-Completion, for example, with IDE's like Jupyter Notebooks, Spyder, etc... as you code through the STK API. Here is the formal documentation for comtypes: https://pythonhosted.org/comtypes/.

Comtypes needs to be able to write the Python wrappers that it creates to a specific location. Running the following code displays the location of the comtypes gen folder containing the wrapper files:
 
import comtypes
from comtypes.client import CreateObject
print(comtypes.client.gen_dir)

This gen folder needs to be written to by the user who is running Python at the time these libraries are created. First check that the user has permission to the comtypes gen folder. If folder permissions are not set, you will see similar errors to the error log above.

If you do have permissions set, check to see if the wrapper files in the comtypes gen folder are being generated. If the folder is not initialized, some of the GUID files (named with a random sequence of numbers and letters) may not generate and are empty. You can verify if this is the problem by opening the files in a text editor and reviewing the contents.

First, attempt to regenerate the comtypes gen folder by following the steps in the FAQ here: https://agiweb.secure.force.com/faqs/articles/Keyword/Python-Integration-Tutorial-Common-Error.
If the error persists, continue to the next solution below.


Comtypes with Other COM Enabled Tools

We can check that this is an issue with the current Python environment by generating a comtypes gen folder through a reference standard: Microsoft Excel. If comtypes works with Excel, then we know we have a Python environment that should work with any COM object, including those in STK.

Executing the following code:
import comtypes
from comtypes.client import CreateObject
xl = CreateObject("Excel.Application")
will cause comtypes to run through the Excel object model (via its Type Libraries), creating files named Excel.py, Office.py, stdole.py, VBIDE.py, etc... in your comtypes gen folder. 

Run the following code to determine the location your comtypes gen folder:
import comtypes.client
print(comtypes.client.gen_dir, '\n')

and check for the files listed above.

If it works, and didn't throw any errors, you should now see "Excel.exe" in your Task Manager, but Excel's GUI isn't visible. You can use the following commands to make it visible, and then subsequently kill it.
xl.visible = True
xl.quit()
Del xl


If this fails, then we know that this is a compatibility issue with the Python environment and comtypes.


Comtypes and Python Compatibility

Check the compatibility of your comtypes and Python versions by running the following code in a new Python interpreter:
 
pip list

This should return a list of modules and their version stamps. Look for “comtypes and confirm it lists as version 1.1.7. Next find the version of Python you are running. One way to do this is to run the code:
 
from platform import python_version
print(python_version())

which should return 3.7.6 or 3.8.1. If you are running the stock install of Anaconda 2020.02, then you should get back version 3.7.6.

Python version 3.7.6 or version 3.8.1 and comtypes 1.1.7 are not compatible and give the error above.

More information on the compatibility between Python versions and comtypes can be found on the comtypes GitHub. You can find the GitHub repo issue pages here: https://github.com/enthought/comtypes/issues. This is where comtypes bugs and related problems are discussed. When looking at issues #200 and #202, we discover that code using comtypes.client.GetModule broke when running Python 3.7.6, as well as Python 3.8.1. These issue pages show that the code worked fine in Python 3.7.3, 3.7.5, and 3.8.2.

We ran compatibility tests utilizing Anaconda’s Python environments. A good test is to create a configuration of a specific Python version, comtypes, and the entire JupyterLab dependency stack. You can run the following commands from an Anaconda Command Shell (CMD) or PowerShell (PS) prompt to create a new conda environment:
conda create -n comtypesTest  python=3.7.7  comtypes  jupyterlab 
conda activate comtypesTest

This will provision and activate a new environment using Python version 3.7.7. We can then run previous STK code, or any COM object code, in JupiterLab to test compatibility.

There is an option to upgrade the base version of Anaconda’s Python to a different version. But this could cause other module relationships and dependencies to break. We recommend working with Python modules in separate conda environments to avoid problems. You can read more on conda environments in the conda documentation here: https://docs.conda.io/en/latest/.

By creating new conda environments and running the integration tutorial code, we have found that compatible Python versions include 3.7.3, 3.7.5, 3.7.7, and 3.8.2.

The solutions to this compatibility problem are as follows:
 
  1. If you are using Anaconda and you are unfamiliar with conda environments, the safest solution is to download the 2019.07 release of Anaconda. This release uses Python version 3.7.3 and is compatible with comtypes 1.1.7. This can be found in the Anaconda installer archive here: https://repo.anaconda.com/archive/. Using this of Anaconda/Python version should generate the gen folder and allow you to continue integrating Python with STK.
 
  1. If you are using Anaconda and you are comfortable with conda environments, you can create a new environment using Python 3.7.7. This can be achieved by running the following command:
    conda create -n newEnvironment python=3.7.7. 

    and then working in the new environment.
    Warning: It is possible that doing so may break other module relationships and dependencies within Anaconda. You can read more about managing environments in Anaconda here: https://docs.conda.io/projects/conda/en/latest/user-guide/tasks/manage-environments.html.
 
  1. If you are not using Anaconda, you need to download a version of Python other than 3.7.6 or 3.8.1. For example, version 3.7.7 or version 3.8.2, which work with comtypes version 1.1.7. Other versions of Python can be found here: https://www.python.org/downloads/.
 
  1. If you are a Windows user and want to avoid configuring Python, you can use other distributions of Python through the WinPython project. This contains a “portable” scientific python distribution that is configured for Windows idiosyncrasies. The download page (located as part of the GitHub repo for the project) is here: https://github.com/winpython/winpython/releases. You want to choose either Winpython64-3.8.2.0cod.exe or Winpython64-3.7.7.0cod.exe for Python version 3.8.2 or version 3.7.7, respectively.

Brute Force

If these solutions do not work for you, there is another FAQ that explains how to “brute-force” the generation of the comtypes gen folder. This method involves dropping the contents of a supplied zip file in the gen folder. This FAQ solution can be found here: https://agiweb.secure.force.com/faqs/articles/Keyword/Having-Trouble-Connecting-to-STK-with-Python.

Note: This “brute-force” method is a temporary solution, but may lead to more issues in the future. This is not recommended as a long term solution.
 
Resource File 1 
Resource File 2