run python3 script on linux apache 2.4 - python

I have looked everywhere and tried many suggested solutions, still without the required result: to run a python file from my lamp server. I can not seem to integrate all the pieces of the puzzle ... Complicating the story is that many solutions either use old apache version (<2.4), which changed the config files significantly. No more httpd.conf! so this executing-a-python-script-in-apache2 does not help; But also the python version being > 3 complicates matters.
specs:
linux Kubuntu, apache 2.4, python 3.5
apache is running
website files are in root/var/www/html/, I have sudo access to this folder.
apache2 cgi module enabled: a2enmod cgi
the python 3.5 path is usr/bin/env python3
the python script, simplest of scripts, has been made executable
#!/usr/bin/env python3
print ("Content-type: text/html\n")
print ("Hello world!")
lets boil it down to the simplest case: I would like to have apache interpret the spark.py script and spit out the html: "Hello world!"
Questions:
is the script file correct as is?
which config files do I need to change and what do I need to add to these config files?
I know for security reasons, you should not have apache run script in your root dir.

The python documentation for modwsgi seems to fit what you are asking for. The following webpage has a really simple example and the necessary configuration for a python3-apache2 setup.
http://modwsgi.readthedocs.io/en/develop/user-guides/quick-configuration-guide.html
You will need to install the mod_wsgi for the configuration to work. Take note of the different "_" underscore and "-" dash character used in apt and pip3.
$ sudo apt install apache2-dev libapache2-mod-wsgi-py3
$ sudo pip3 install mod_wsgi
libapache2-mod-wsgi-py3 and mod_wsgi seems to be the same thing. However, my test deployment only works after installing mod_wsgi. Could be configuration issue. The following are the details of the configuration I have tested on Ubuntu 16.04.2.
Application file /home/user/wsgi_sample/hello.wsgi:
def application(environ, start_response):
status = '200 OK'
output = b'Hello World!'
response_headers = [('Content-type', 'text/plain'),
('Content-Length', str(len(output)))]
start_response(status, response_headers)
return [output]
Apache2 configuration /etc/apache2/sites-available/000-test.conf
<VirtualHost *:80>
ServerName testmachine
<Directory /home/user/wsgi_sample>
Order allow,deny
Allow from all
Require all granted
</Directory>
WSGIScriptAlias /hello /home/user/wsgi_sample/hello.wsgi
</VirtualHost>
Enable the site in apache2.
sudo a2ensite 000-test.conf
Open your browser to testmachine/hello.
wsgi may also be deployed on Apache2 using passenger. It demands a slighter longer configuration. Ask a new question if passenger/python3 is desired.

Yes, your minimum code seem correct. The Apache config information is answered here
https://stackoverflow.com/a/57531411/4084546

Related

How do I properly configure a Python Flask app to be served by Apache?

I've been trying to sort this out for ages but I just can't seem to get it to work.
Basically I want to use mod_wsgi with apache to serve my Python Flask app, what am I missing?
This is what I've got, a python flask app (flask_restful) with the a main.py as follows:
from app import create_app
application = create_app()
application.run(debug=True)
which calls my app.py
def create_app() -> Flask:
errors = WWAPIErrors()
errors.add_error(GeneralException, 400)
app = Flask("namehere")
api = WWAPI(error_list=errors, app=app)
# APIS
api.add_resource(endpointResouceClass, '/endpoint')
return app
It all runs locally correctly, I have a VPS set up with other sites running perfectly but no python flask apps.
So I've done the following:
sudo apt-get install libapache2-mod-wsgi-py3
sudo apt-get install apache2-dev
sudo apt-get install python3-dev
cd /var/www/appDirectory
python3 -m venv venv
source venv/bin/activate
pip install mod_wsgi
pip install -r requirements.txt
My website.conf file in the /etc/apache2/sites-available directory is:
<VirtualHost *:80>
ServerName example.com
ServerAlias www.example.com
ServerAdmin email#email.com
WSGIScriptAlias / /var/www/appDirectory/app/api/main.py
DocumentRoot /var/www/appDirectory/app/api
<Directory /var/www/appDirectory/app/api/main.py>
Require all granted
</Directory>
WSGIDaemonProcess localhost python-path=/var/www/appDirectory/venv/lib/python3.10/site-packages/ user=www-data
Alias /api /var/www/appDirectory/app/api
ErrorLog ${APACHE_LOG_DIR}/error.log
CustomLog ${APACHE_LOG_DIR}/access.log combined
</VirtualHost>
Then I set my mod_wsgi config files:
sudo a2enmod wsgi
mod_wsgi-express module-config
LoadModule wsgi_module "/home/user/appDirectory/venv/lib/python3.10/site-packages/mod_wsgi/server/mod_wsgi-py310.cpython-310-x86_64-linux-gnu.so"
WSGIPythonHome "/home/user/appDirectory/venv"
and put that in my /etc/apache2/mods-enabled/wsgi.load file.
Next I enabled my site:
cd /etc/apache2/sites-available
sudo a2ensite mysitename.conf
The directory of my project loads when I go to the base URL for my app because I have no index.html or anything on site.com/ root directory. But when I go to my implemented site url which is site.com/endpoint I just get a 404, I've even tried to get it locally on my VPS and no luck.
wget localhost:80/endpoint
--2022-12-08 21:07:15-- http://localhost/endpoint
Resolving localhost (localhost)... 127.0.0.1
Connecting to localhost (localhost)|127.0.0.1|:80... connected.
HTTP request sent, awaiting response... 404 Not Found
2022-12-08 21:07:15 ERROR 404: Not Found.
I know/hope I'm just missing something stupid, any help would be GREATLY appreciated.
System details:
neofetch
.-/+oossssoo+/-.
`:+ssssssssssssssssss+:` -------------
-+ssssssssssssssssssyyssss+- OS: Ubuntu 22.04.1 LTS x86_64
.ossssssssssssssssssdMMMNysssso. Host: VMware Virtual Platform None
/ssssssssssshdmmNNmmyNMMMMhssssss/ Kernel: 5.15.0-52-generic
+ssssssssshmydMMMMMMMNddddyssssssss+ Uptime: 47 days, 10 hours, 49 mins
/sssssssshNMMMyhhyyyyhmNMMMNhssssssss/ Packages: 1392 (dpkg), 7 (snap)
.ssssssssdMMMNhsssssssssshNMMMdssssssss. Shell: bash 5.1.16
+sssshhhyNMMNyssssssssssssyNMMMysssssss+ Resolution: 1024x768
ossyNMMMNyMMhsssssssssssssshmmmhssssssso Terminal: /dev/pts/0
ossyNMMMNyMMhsssssssssssssshmmmhssssssso CPU: Intel Xeon E5-2683 v3 (2) # 1.997GHz
+sssshhhyNMMNyssssssssssssyNMMMysssssss+ GPU: 00:0f.0 VMware SVGA II Adapter
.ssssssssdMMMNhsssssssssshNMMMdssssssss. Memory: 987MiB / 1941MiB
/sssssssshNMMMyhhyyyyhdNMMMNhssssssss/
+sssssssssdmydMMMMMMMMddddyssssssss+
/ssssssssssshdmNNNNmyNMMMMhssssss/
.ossssssssssssssssssdMMMNysssso.
-+sssssssssssssssssyyyssss+-
`:+ssssssssssssssssss+:`
.-/+oossssoo+/-.
I managed to find my problem:
Apparently wsgi can't use main.py file directly. I needed to include an app.wsgi file in the root of my project directory, with the following contents:
import sys
sys.path.insert(0, '/var/www/appDirectory/app/api')
from main import application
In addition to this I needed to edit my main.py file to remove the application.run() line as wsgi handles that itself. So my main.py file now looks like this:
from app import create_app
application = create_app()
Now when I run my application I no longer get a 404 but I get the correct response with a 200 code.
Hopefully this helps someone else at some stage, as I do think the information about mod_wsgi and wsgi is really lacking and conflicting online.

Trouble hosting Django website in Ubuntu (Error)

I need to host a Django website in Ubuntu 18 (Desktop). I searched the web but couldn't find a well-written tutorial which demonstrates how to do this step by step. After doing some research I came across following procedure but I believe its incomplete.
Library installed
sudo apt-get install python3.6
pip3 install Django
sudo apt-get install apache2
sudo apt-get install libapache2-mod-wsgi
The project named mysite with an app polls and virtual environment mysite_env is located in /var/www with following directory structure
Configured wsgi.py at follows
import os
import sys
from django.core.wsgi import get_wsgi_application
sys.path.append('/var/www/mysite')
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'mysite.settings')
application = get_wsgi_application()
Added following lines in apache2.conf located in etc/apache2/apache2.conf
#ServerName mysite.com
WSGIScriptAlias / /var/www/mysite/mysite/wsgi.py
WSGIPythonHome /var/www/mysite/mysite_env
#WSGIPythonPath /path/to/mysite.com
<Directory /var/www/mysite/mysite>
<Files wsgi.py>
Require all granted
</Files>
</Directory>
If everything setups perfectly then on opening localhost in the browser will let Apache server to open Django app but on the other hand, by doing it Django app doesn't loads.
I am missing lots of things I know, I need to host it and access it on the web. Can anybody tell me what steps I am missing, Any suggestions would be of great help.
References
https://docs.djangoproject.com/en/1.10/howto/deployment/wsgi/modwsgi/y
I followed this simple step to step tutorial which I can recommend. It is for Ubuntu 16.04 but I believe you can simply transfer it to 18.04
https://simpleisbetterthancomplex.com/tutorial/2016/10/14/how-to-deploy-to-digital-ocean.html

How to run Python within a virtualenv with WSGI?

I'm trying to run Python within a sandbox using WSGI and Apache.
I created the virtual environment:
virtualenv /var/www/demo-environment --python /usr/bin/python3.3
I also created the following /var/www/demo.py file:
#!/usr/bin/env python
import sys
def application(environ, start_response):
start_response('200 OK', [('Content-Type', 'text/plain')])
return "Running " + str(sys.version_info)
Finally, I changed Apache configuration like this:
WSGIPythonPath /var/www/demo-environment/lib/python3.3/site-packages/
WSGIDaemonProcess example.com python-path=/var/www/demo-environment/lib/python3.3/site-packages/
WSGIProcessGroup example.com
WSGIScriptAlias / /var/www/demo.py
When going to the home page of the website, it shows the following contents: Running sys.version_info(major=2, minor=7, micro=5, releaselevel='final', serial=0), indicating that while Python works, it is not called within a virtual environment.
Since this is the wrong way to enable virtualenv, which is the right one?
Just use the setting WSGIPythonHome to specify the root of your env:
WSGIPythonHome /home/grapsus/work/python/env
WSGIScriptAlias /demo /home/grapsus/work/python/demo.py
I modified your script to print sys.path:
Running ['/home/grapsus/work/python/env/lib/python2.7', ...

Trying to get Pyramid running under Apache + mod_wsgi but it's failing

I've got Apache2 running with mod_wsgi installed. I've confirmed that mod_wsgi actually works by following this.
The problem comes when I try to get Pyramid running. I get an Internal Server Error and my Apache error log contains the exception:
AssertionError: The EvalException middleware is not usable in a multi-process environment
Here's my VHost:
<VirtualHost *:80>
ServerName pyramidtest.dev
DocumentRoot /srv/pyramidtest.dev/www/
AssignUserID pyramidtest nogroup
WSGIScriptAlias / /srv/pyramidtest.dev/pyramid/load.wsgi
</VirtualHost>
Here's my load.wsgi:
import site
site.addsitedir('/opt/pyramid/lib/python2.7/site-packages')
from pyramid.paster import get_app
application = get_app('/srv/pyramidtest.dev/pyramid/test/development.ini', 'main')
mod_wsgi is compiled to use /opt/python2.7 as the Python interpreter but I'm running Pyramid under a virtualenv in /opt/pyramid - This is why I have the site.addsitedir() in my load.wsgi.
And, in case it's needed, apache2 -V:
Server version: Apache/2.2.9 (Debian)
Server built: Dec 30 2010 11:50:24
Server's Module Magic Number: 20051115:15
Server loaded: APR 1.2.12, APR-Util 1.2.12
Compiled using: APR 1.2.12, APR-Util 1.2.12
Architecture: 32-bit
Server MPM: ITK
threaded: no
forked: yes (variable process count)
Server compiled with....
-D APACHE_MPM_DIR="server/mpm/experimental/itk"
-D APR_HAS_SENDFILE
-D APR_HAS_MMAP
-D APR_HAVE_IPV6 (IPv4-mapped addresses enabled)
-D APR_USE_SYSVSEM_SERIALIZE
-D APR_USE_PTHREAD_SERIALIZE
-D SINGLE_LISTEN_UNSERIALIZED_ACCEPT
-D APR_HAS_OTHER_CHILD
-D AP_HAVE_RELIABLE_PIPED_LOGS
-D DYNAMIC_MODULE_LIMIT=128
-D HTTPD_ROOT=""
-D SUEXEC_BIN="/usr/lib/apache2/suexec"
-D DEFAULT_PIDLOG="/var/run/apache2.pid"
-D DEFAULT_SCOREBOARD="logs/apache_runtime_status"
-D DEFAULT_LOCKFILE="/var/run/apache2/accept.lock"
-D DEFAULT_ERRORLOG="logs/error_log"
-D AP_TYPES_CONFIG_FILE="/etc/apache2/mime.types"
-D SERVER_CONFIG_FILE="/etc/apache2/apache2.conf"
What am I missing...?
You're using the EvalException middleware (as can be seen from your error message). This solution to this error is actually covered in the Debugging Techniques wiki of mod_wsgi.
Basically, since the middleware allows browser-based interactive debugging of your application, all requests need to be sent to the same process; however, you are running mod_wsgi in embedded mode, which can create many processes by default.
From the wiki:
[...] if you want to be able to use this
browser based interactive debugger, if
running your application in embedded
mode of mod_wsgi, you will need to
configure Apache such that it only
starts up one child process to handle
requests and that it never creates any
additional processes. The Apache
configuration directives required to
achieve this are as follows.
StartServers 1
ServerLimit 1
Switching to daemon mode (with a single process, the default) will also fix this problem, and is recommended over running in embedded mode. Here are the Apache directives:
WSGIDaemonProcess pyramidtest.dev display-name=%{GROUP}
WSGIProcessGroup pyramidtest.dev
mod_wsgi can also add the path to the Python path for you. If using embedded mode you can use:
WSGIPythonPath /opt/pyramid/lib/python2.7/site-packages
If using daemon mode, instead use the 'python-path' option to the WSGIDaemonProcess directive.
WSGIDaemonProcess pyramidtest.dev display-name=%{GROUP} python-path=/opt/pyramid/lib/python2.7/site-packages
WSGIProcessGroup pyramidtest.dev

Invalid command 'WSGIReloadMechanism' in my Apache site's config file

I am trying to deploy a Django project and am using Apache2 with mod_wsgi. Here are the relevant lines in my Apache conf file:
WSGIScriptReloading On
WSGIDaemonProcess myprojectcom
WSGIReloadMechanism Process
WSGIProcessGroup myprojectcom
WSGIApplicationGroup myprojectcom
WSGIPassAuthorization On
WSGIScriptAlias / /home/myproject/myproject/deploy/deploy.wsgi
I've used a very similar conf file for many other deployments, but this is the first time that I'm getting the following error:
/etc/apache2/sites-available$ sudo /etc/init.d/apache2 restart
Syntax error on line 8 of /etc/apache2/sites-enabled/myproject.com:
Invalid command 'WSGIReloadMechanism', perhaps misspelled or defined by a module not included in the server configuration
Action 'configtest' failed.
The Apache error log may have more information.
...fail!
I don't see any syntax error, though. I'm on Ubuntu, using the libapache2-mod-wsgi package. What could be wrong?
Remove the whole line:
WSGIReloadMechanism Process
It isn't needed any more and the directive was removed completely in mod_wsgi 3.X.
You should preferable not rely on old blog posts for how to set up mod_wsgi and use the actual mod_wsgi documentation on the mod_wsgi site instead.

Categories

Resources