Latest update: The problem had indeed to do with permission and user groups, today I learned why we do not simply use root for everything. Thanks to Jakub P. for reminding me to look into the apache error logs and thanks to domoarrigato for providing helpful insight and solutions.
What's up StackOverflow.
I followed the How To Deploy a Flask Application on an Ubuntu VPS tutorial provided by DigitalOcean, and got my application to successfully print out Hello, I love Digital Ocean!
when being reached externally by making a GET
request to my public server IP.
All good right? Not really.
After that, I edit the tutorial script and write a custom flask application, I test the script in my personal development environment and it runs without issue, I also test it on the DigitalOcean server by having it deploy on localhost and making another GET
request.
All works as expected until I try to access it from my public DigitalOcean IP, now suddenly I am presented with a 500 Internal Server Error
.
What is causing this issue, and what is the correct way to debug in this case?
Setting app.debug = True
gives the same 500 Internal Server Error
without a debug report.
Running the application on the localhost of my desktop pc and DigitalOcean server gives no error, the script executes as expected.
The tutorial code runs and executed fine, and making a GET
request to the Digital Ocean public IP returns the expected response.
I can switch between the tutorial application and my own application and clearly see that I am only getting the error wit my custom application. However the custom application still presents no issues running on localhost.
from flask import Flask, request, redirect
from netaddr import IPNetwork
import os
import time
app = Flask(__name__)
APP_ROOT = os.path.dirname(os.path.abspath(__file__))
# Custom directories
MODULES = os.path.join(APP_ROOT, 'modules')
LOG = os.path.join(APP_ROOT, 'log')
def check_blacklist(ip_adress):
ipv4 = [item.strip() for item in open(MODULES + '//ipv4.txt').readlines()]
ipv6 = [item.strip() for item in open(MODULES + '//ipv6.txt').readlines()]
for item in ipv4 + ipv6:
if ip_adress in IPNetwork(item):
return True
else:
pass
return False
@app.route('/')
def hello():
ip_adress = request.environ['REMOTE_ADDR']
log_file = open(LOG + '//captains_log.txt', 'a')
with log_file as f:
if check_blacklist(ip_adress):
f.write('[ {}: {} ][ FaceBook ] - {} .\n'
.format(time.strftime("%d/%m/%Y"), time.strftime("%H:%M:%S"), request.environ))
return 'Facebook'
else:
f.write('[ {}: {} ][ Normal User ] - {} .\n'
.format(time.strftime("%d/%m/%Y"), time.strftime("%H:%M:%S"), request.environ))
return 'Normal Users'
if __name__ == '__main__':
app.debug = True
app.run()
from flask import Flask
app = Flask(__name__)
@app.route("/")
def hello():
return "Hello, I love Digital Ocean!"
if __name__ == "__main__":
app.run()
Seems like the following line could be a problem:
log_file = open(LOG + '//captains_log.txt', 'a')
if the path its looking for is: '/var/www/flaskapp/flaskapp/log//captains_log.txt'
that would make sense that an exception is thrown there. Possible that the file is in a different place, on the server, or a /
needs to be removed - make sure the open
command will find the correct file.
If captains_log.txt
is outside the flask app directory, you can copy it in and chown it. if the txt file needs to be outside the directory then you'll have to add the user to the appropriate group, or open up permissions on the actual directory.
chown command should be:
sudo chown www:www /var/www/flaskapp/flaskapp/log/captains_log.txt
and it might be smart to run:
sudo chown -r www:www /var/www