Python script that leaves an activated virtualenv after it halts [duplicate] - python

This question already has answers here:
How to source virtualenv activate in a Bash script
(12 answers)
Closed 1 year ago.
This post was edited and submitted for review 1 year ago and failed to reopen the post:
Duplicate This question has been answered, is not unique, and doesn’t differentiate itself from another question.
I'm trying to create a utility CLI that creates an empty python project with just a .venv inside.
One of the features I wanted is that, when the CLI ends the project creation, it leaves the bash inside the project folder and with the virtualenv activated. This way:
(base) ubuntu#pc:~/dev/cli$ python cli.py start ./folder
... do it's magic ...
... and ends up like this:
(.venv) ubuntu#pc:~/dev/cli/folder$
Note that now the cwd is inside folder and **(.venv) ** is activated.
I was able to achieve part of my objective (change the folder) by using:
import os
os.chdir("./folder")
os.execl("/bin/bash", "/bin/bash")
But didn't find a way to keep the venv activated after the program is halted.
Any ideas??

bash has the -rcfile option that allows to use a non standard initialization file.
import os
os.chdir("./folder")
os.execl("/bin/bash", "/bin/bash", "--rcfile", ".venv/bin/activate")
That should be enough for the new .venv to be active in the bash shell.

Related

/usr/bin/env: python3: No such file or directory when running script from cron [duplicate]

This question already has answers here:
How to get CRON to call in the correct PATHs
(15 answers)
Closed 6 months ago.
My BASH scrit has following line:
video_id=$(/usr/local/bin/yt-dlp --no-warnings --get-id "$ChannelPath")
it succeeds when runs from command line under certain user.
When it runs from cron, under the same user, it results in:
/usr/bin/env: python3: No such file or directory
What could be different in these two cases?
CentOS 7
Python 3.11.0a4
There are some discussions whether you should use #!/usr/bin/env python or #!/usr/bin/python. Proponents of the env variant say that it is better, because env uses the PATH to find the interpreter, and opponents say that the problem with the env variant is that it uses the PATH.
I dislike env, therefore I will give you a solution without it.
From the command line type
which python3
This will give you something like
/usr/bin/python3
In /usr/local/bin/yt-dlp, replace the first line with
#!/usr/bin/python3
(the output that you got from the which command.)
Or call /usr/local/bin/yt-dlp with explicitly the right interpreter:
video_id=$(/usr/bin/python3 /usr/local/bin/yt-dlp --no-warnings --get-id "$ChannelPath")
it succeeds when runs from command line under certain user.
When it runs from cron, under the same user, it results in:
/usr/bin/env: python3: No such file or directory
What could be different in these two cases?
The difference is the environment in which the script runs. In particular, the environment variables in it, and most particularly, the PATH.
When a user runs the script from the command line, it inherits the environment from which it was launched, which includes system-wide and possibly user-specific customizations that are engaged only for interactive shells. (For example, the contents of the user's ~/.bash_profile and / or ~/.bashrc files.) By default, when a shell is launched noninteractively (by cron, for example) it does not read or execute any environment configuration.
Evidently,
Your /usr/local/bin/yt-dlp is or attempts to launch a Python script that has a shebang line using /usr/bin/env to choose and launch the python3 binary. That is, the affected script starts with
#!/usr/bin/env python3
These days, that form is widely used and recommended in the Python world. The purpose is to use the PATH to locate the python3 binary to use, as opposed to hard-coding that into the script. However,
There is no system Python 3 installed on the machine. (That is, none installed in the default path.) The user who runs the script successfully is able to do so because they have an environment configured with some non-default directory in their PATH from which python3 can be launched.
One possible solution would be to install CentOS's Python 3:
sudo yum install python3
If you need a different version of Python 3 (CentOS 7's is version 3.6) then you can instead set an appropriate PATH in the relevant crontab file, maybe something like
PATH=/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin
0 * * * * /path/to/my_script
Alternatively, you could modify your shell script to set the path there:
PATH=/usr/local/bin:$PATH
video_id=$(/usr/local/bin/yt-dlp --no-warnings --get-id "$ChannelPath")
or you could modify /usr/local/bin/yt-dip by altering its shebang (supposing that this is the affected Python script).
I moved the python3 symlink from /usr/local/bin to /usr/bin and it works now.
/usr/local/bin was the suggested location in internet-manuals about how to compile and install Python 3.11 in CentOS7.
A better solution is to add
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/root/bin
to the first line of crontab. Although it should be not /etc/crontab, but
crontab -l > crontab.txt
then edit crontab.txt
then
crontab crontab.txt

Django can't recognize bash variable even if I export it - running virtual server from Pycharm [duplicate]

This question already has answers here:
Pycharm: set environment variable for run manage.py Task
(16 answers)
Closed 5 years ago.
I have an environment variable exported in bash. Project is in localhost. OS is Debian 9 Stretch.
When I run, in command line:
python -c "import os; print(os.environ.get('EMAIL_PASSWORD'))"
I get the variable value.
But, inside Django, calling os.environ.get('EMAIL_PASSWORD') returns None.
In settings:
EMAIL_HOST_PASSWORD = os.environ.get('EMAIL_PASSWORD')
Already find n similar questions, but in general the problem is that the variable wasn't exported to environment.
What I am missing?
Update:
Django virtual server is called directly from Pycharm
export $EMAIL_PASSWORD will not work. First remove the $ and define the variable value in the shell, not only the variable name. It should look like this: export EMAIL_PASSWORD='value'
Edit
Don't put the ''around the var when you call it. Django will think its a string, not a variable.

How to tell, from within a running script, what Python interpreter is running it? [duplicate]

This question already has answers here:
Find full path of the Python interpreter?
(3 answers)
Closed 6 years ago.
I would like to output, in my script, the full path of the Python interpreter running it:
#!/usr/bin/env python
print("{}".format(full_path_of_interpreter_running_this_script)
The script is in the PATH and run as:
script.py
Can I do that? How?
Note: Doing which python or type python in bash does not help me, because I am using pyenv, and pyenv is doing shims magic.
Note: More than identifying the Python executable, I am interested in identifying the virtualenv that is being used, and I thought knowing the full path to the interpreter will help me in this.
This gives the full path to the command that was used to run the script:
import sys
print(sys.executable)

cd to dir after exiting script (system independent way, purely in python) [duplicate]

This question already has answers here:
How do I set the working directory of the parent process?
(8 answers)
Change directory of parent process after exit [duplicate]
(2 answers)
Closed 9 years ago.
Observe the following:
$ pwd
/home/username
$ python
>>> import os
>>> os.chdir("/")
# Ctrl + D
$ pwd
/home/username
But I want to be in the / dir after exiting the python interpreter, is that possible using python?
I would like to know because I want to make a platform independent script(using python) where an optional convenience command cd's the user into a certain directory.
But I want to be in the / dir after exiting the python interpreter, is that possible using python?
It is not possible. Neither by using Python or any other "acceptable" way. By acceptable, I mean "without outrageously hacking your system (with gdb for example)" ;)
More seriously, when the user launch an executable from a shell, the child process will run in its own environment, which is mostly a copy of its parent environment. This environment contains "environment variables" as well as the "current working directory", just to name those two.
Of course, a process can alter its environment. For example to change its working directory (like when you cd xxx in you shell). But since this environment is a copy this does not alter the parent's environment in any way. And there is no standard way to access your parent environment.

How transform a python program .py in an executable program in Ubuntu? [duplicate]

This question already has answers here:
What do I use on linux to make a python program executable
(8 answers)
Closed 7 years ago.
I have a simple python program and I want an executable version (for Ubuntu Linux) of this program to avoid running it in the terminal with python myprogram.py.
How can I do that ?
There is no need to. You can mark the file as executable using
chmod +x filename
Make sure it has a shebang line in the first line:
#!/usr/bin/env python
And your linux should be able to understand that this file must be interpreted with python. It can then be 'executed' as
./myprogram.py
As various others have already pointed out you can add the shebang to the top of your file
#!/usr/bin/python or #!/usr/bin/env python
and add execution permissions chmod +x program.py
allowing you to run your module with ./program.py
Another option is to install it the pythonic way with setuptools. Create yourself a setup.py and put this in it:
from setuptools import setup
setup(
name = 'Program',
version = '0.1',
description = 'An example of an installable program',
author = 'ghickman',
url = '',
license = 'MIT',
packages = ['program'],
entry_points = {'console_scripts': ['prog = program.program',],},
)
This assumes you've got a package called program and within that, a file called program.py with a method called main(). To install this way run setup.py like this
python setup.py install
This will install it to your platforms site-packages directory and create a console script called prog. You can then run prog from your terminal.
A good resource for more information on setup.py is this site: http://mxm-mad-science.blogspot.com/2008/02/python-eggs-simple-introduction.html
You can try using a module like cxfreeze
At the top op your python program add:
#!/usr/bin/python
I know the easiest, exact and the best solution. I had the same problem like you but now, I can run my Python/Tkinter(GUI) program with its icon.
As we create .bat files on Windows, we can also create equivalent the .bat files easily in Linux too. Thanks to this file, that, we can start our programs without terminal even if it needs to get command on terminal to start (like Python programs) with double click to its icon (really .png icon :) ) or we can write commands to facilitate our works.
So, how is this going to happen ?
For example, if we want to run our .py program, we just need to write this command to terminal :
python3 locationOfPyFile
So if we create a file that can automatically run this command, problem would be solved. In addition to that, you can have your own icon and even you don't have to open terminal !
Check this article : Run Commands From It's Icon (Easiest Way)

Categories