Python Modules and submodules in ROS catkin workspace - python

I am trying to run python code in ROS and it includes a module (module not made for ROS) that I had to pip install. When I try running the code in my catkin workspace with roscore running, it cannot find the module I installed and gives me an ImportError. Any idea on how to run already created modules on ROS with rospy?

Making sure you can find the module
Here are 3 options. They all should work and are in order of hackiness.
You can add the module to a package.xml like in this ros numpy tutorial.
<build_depend>python-numpy</build_depend>
<run_depend>python-numpy</run_depend>
Set your $PTYHONPATH environment variable in your .bashrc:
export PYTHONPATH=$PYTHONPATH:/path/to/your/package_or_module
Inject a path to the module before importing it in your python code:
import sys
sys.path.insert(0, "/path/to/your/package_or_module")
Making sure you're running the program correctly
Resource your .bashrc and catkin workspace before running the program.
If you are trying to use rosrun package_name filename.py then you need to make sure the file is an executable:
chmod +x pythonfile.py
and the top of the python file should have the code:
#!/usr/bin/env python
Consider using python directly to run the file like akshayk07 mentioned
python filename.py

Related

Python Path For Local Import Git Bash

How should git bash be set up to run an non pip installed python library?
I am trying to run a Python library that I have git cloned (not pip installed) on Windows using git bash. I keep getting an error that the module cannot be found even though I have set the $PYTHONPATH to point to this folder.
This occurs both when using a venv and the base environment.
I've activated the venv using the activate command in the venv folder, and then added the folder to the PYTHONPATH as is shown here (excuse the blanking):
The first line shows the error I get when running the script which calls in other modules. The second shows my PYTHONPATH, the third my PATH
Adding the local folder to the path is how this functionality works on mac.
This the particular file that is meant to run, datagen.py:
#!/usr/bin/env python
from msq_data_gen.cli import cli
if __name__ == '__main__':
cli.datagen()
The code fails on the first import of msq_data_gen.
The structure of the program is as so:
Curiously, the integrated running of Pycharm works correctly, but as the code is based off a CLI, this isn't the intended usecase. (I could also use the unit testing mode for click, but I think an answer for this could be useful for other people!)

Python Package on GitHub

I made a python (3) package and I have been trying to upload it on Github. I also know how to push and install a git using pip. To test if it works as anticipated, I made a virtual environment on my local computer (linux) and pip installed my already pushed private package in there without a problem.
The issue is that I don't know how to access it!!! (I know how to activate and use virtualenvs; I don't know how to call my package) My package has a main interface that one would need to call it in terminal as follows:
python3 myui.py some_args *.data
and it's supposed to create some files where it's called. In other words, it's not exactly a module like numpy to be imported. I have watched/read many tutorials and documentations on the web and tbh I'm lost here.
You are looking for the -m flag. If you installed everything correctly, then the following command should allow you to run your script (based on your example). Note that you shouldn't add the file extension '.py'.
python3 -m myui some args *.data
If you have an actual package (directory with __init__.py file and more) instead of a module (a single .py file), then you can add a __main__.py file to that package. Python will execute this script when you use the -m flag with the package's name, in the same way as shown above.
python3 -m mypackage some args *.data
If you want to run a different script that is nested somewhere inside of that package, you can still run it by specifying its module name:
python3 -m mypackage.subpackage.myscript some args *.data
Another common way to make your script available uses the setup script (setup.py) or setup configuration file (setup.cfg) that is used to install the module or package. In that case, you can add an entry point to map a command to a specific module/function/etc. (as described in this Python packaging tutorial) so that you can run that command instead of having to use the -m flag with Python.
$ mycommand some args *.data

Debug python library

I have no idea how to debut a library without installing it, I want to enhance this library, but if I run PyCharm with this configuration:
Pycharm debug configuration
I never collaborated on github or similar, however I decided to join this Hacktoberfest. What configuration should I use? In case I have to install it, how can I put the breakpoints easily?
Edit for more info:
Package has 3 modules:
scdl
|
|-------- client.py
|--------------- scdl.py
|--------------------utils.py
When I run the scdl.py module which has a main it tries to import the client and utils modules, however It can't find them for some reason, I tried to add the directory where the scdl package is stored to the PYTHONPATH variable, and still got no result
Screenshot of PyCharm Directory
The error is:
from scdl import client, utils
ImportError: cannot import name 'client'
When working on something that's intended to be a module, I usually install the module in my interpretter then use the "module_name" run configuration in PyCharm instead of the "script_path" like you have set up.
Create a virtual environment: python -m venv venv
Activate the virtual environment: source venv/bin/activate
Follow the instructions in the projects readme to install (in this case python setup.py install)
Add that virtual environment to PyCharm (Preferences > Project Interpreter)
PyCharm will prompt you to install requirements, do it
Where it says "script_path" in your run configuration, click the little arrow and change to "module_name"
Set the module name to "scdl.scdl"
Now you should be able to run/debug as normal, hope that helps!

Script working in ipython but not from the command line

I have a script that functions from within ipython but when I try and run the same script from the command line I receive import errors for a local module that I am trying to import:
from helper_functions.email_from_server import send_email
Error:
ImportError: No module named helper_functions.email_from_server
This script imports from within Ipython without any issues.
Comparatively, I have code that runs without any issues within ipython I can run another script using the command:
run script.py
From the command line I can run the same script:
python /dir/script.py
However this python /dir/script.py doesn't work with the script with local imports (from above) and I can't figure out if its a pythonpath issue or some local env issue? I have been reading through stack to find it but haven't been able to thus far. It feels like its just around the corner
One attempted solution:
PYTHONPATH=/dir/ python /dir/script.py
EDIT (to help clarify):
I am using an anaconda distribution on a linux machine.
Mucking about with PYTHONPATH is a recipe for sadness. You can do it, but you shouldn't. The correct thing to do is install your package in your correct environment. If you don't know how to create a package here's a super simple example. There may be some differences in your path when running via ipython vs command line.
You can find out what the differences are by using sys.executable and sys.path:
import sys
print(sys.executable)
print(sys.path)
Run that from IPython, and then run that from the python on your command line. You will undoubtedly get two different results. Since you're running Anaconda, you want to follow their guide for installing non-conda packages to install the one that you build.
Though of course that assumes that you've got the anaconda python on your path - you can check that out with which python since you're on Linux.
I resolved it via creating a wrapper shell script. Ugly in that i'm exporting the python path each time, but it works.
#!/bin/bash
export PYTHONPATH="${PYTHONPATH}:/my/dir"
source ~/.bash_profile
cd /my/dir && my/anaconda/location/bin/python /my/dir/to/script/cript.py

Python module visiable only in iPython

I have used set PYTHONPATH=%PYTHONPATH%;dictionary_containing_modules to make some modules globaly visiable.
I have a script importing the modules with import my_module.
When i run the script from the iPython shell (run my_script.py), i get no errors and the script runs as intended, but when I run the script from the command promt (windows) with python my_script.py I get the error:
ImportError: No module named my_module
I checked with pwd that they use the same working directory.
Remember that you can dynamically change your system path from within your script, using sys.path or the site module. So maybe you want to add them to your script...
Or maybe you want to write a BAT or Python launcher script that sets the PYTHONPATH...
Or you want to edit the Windows environment variables (somewhere inside System properties Win+Break).

Categories