Vanaf het Plus-pakket kun je nu een Python-webapplicatie draaien op je hostingpakket. Het opzetten van zo’n webapplicatie verg iets meer voorbereiding dan bijvoorbeeld het uploaden van een PHP-website. Wil je beginnen met Python, dan leg ik je graag stap voor stap uit hoe je dit aanpakt.
Inhoudsopgave
Basisbenodigdheden
Python-ondersteuning is bij Antagonist beschikbaar vanaf het Plus-pakket. Kun je de Python-selector in het DirectAdmin-menu niet vinden, bekijk dan in Mijn Antagonist welk hostingpakket je hebt. Je kunt dat zien op de productpagina. Voor het installeren en testen van de Python-webapplicatie is het ook handig dat je weet hoe je een SSH-verbinding met je pakket kunt maken.
Belangrijke kanttekeningen
- Met deze uitleg zet je direct op productie een webapplicatie op. Volg het alleen als je op jouw domein geen belangrijke website hebt draaien. Er bestaat een risico dat je de bestaande website beschadigt.
- Deze uitleg is puur geschikt voor een testproject. Zorg dat je een nieuwe productiewebsite eerst lokaal of op een testomgeving bouwt.
- Vul geen belangrijke (klant)informatie in deze testapplicatie in, voordat je begrijpt hoe de beveiliging van Django werkt.
Python-webapplicatie aanmaken
Het toevoegen van een Python-webapplicatie begint in DirectAdmin. Ga in het menu naar Extra functies → Python Selector en klik op ‘Create application’ om met een nieuwe webapplicatie te beginnen.
Er verschijnen nu een aantal velden. Het ene veld is intuïtiever dan het andere, daarom licht ik ze graag elk even toe.
- Python version | Geeft aan onder welke Python-versie je omgeving wordt aangemaakt. Python 2.7 is sterk verouderd, dus ik zou adviseren om hier Python 3.7 te selecteren.
- Application root | Bepaalt in welke map je project komt te staan. Deze waarde is vaak de projectnaam van je webapplicatie. Gebruik hier geen submap om problemen met pip-pakketten installeren te voorkomen. Wil je een subpad gebruiken, stel dit dan in bij ‘Application URL’.
- Application URL | Dit is standaard de URL van je website met de ‘application root’ als pad (voorbeeld.nl/demo). Je kunt ook het project op de URL draaien zonder pad. Vul dan gewoon je domein in (voorbeeld.nl).
- Application startup file | Dit is het aanknopingspunt voor onze server om te kunnen bepalen hoe jouw webapplicatie wordt geserveerd. Laat je dit veld leeg bij het voor de eerste keer opslaan, dan wordt er standaard een passenger_wsgi.py-bestand aangemaakt en gelinkt. Als je een Django-applicatie aanmaakt of uploadt, dan wil je deze waarde achteraf aanpassen naar de bijbehorende wsgi.py. Dit volgt later in deze uitleg.
- Application Entry point | De ondertekst bij dit veld doet vermoeden dat dit de plek is waar je linkt naar de wsgi.py van je webapplicatie, maar dit werkt niet als zodanig. Laat dit veld leeg, zodat hier de standaardwaarde ‘application’ wordt ingevuld.
- Passenger log file | Vul hier de bestandsnaam in waar de standaard passenger_wsgi naar kan loggen (bijvoorbeeld ‘passenger.log’). Hierin worden eventuele problemen gelogd die Passenger wsgi bij het inladen van je webapplicatie ondervindt.
Nieuwe Python-webapplicatie gebruiken
Als je alle instellingen naar wens hebt ingevoerd, dan klik je op ‘Create’. Na het opslaan van de nieuwe configuratie, zie je dan hoe je via SSH je virtualenv activeert en naar je projectmap navigeert.
Let op dat de inhoud van je project dus niet in public_html-map staat, maar in:
/home/<deb12345>/<projectnaam>
Dit is ook de locatie waar je wijzigingen in de webapplicatie naar wilt uploaden met SFTP of SCP. In de public_html-map heb je ook een map met een vergelijkbare naam, maar hierin staat enkel een .htaccess-bestand. Die zorgt ervoor dat de server jouw webapplicatie kan vinden.
Virtualenv
Je virtualenv is een hulpmiddel om alle benodigde pip-pakketten (en de versie van Python) in de context van een specifieke webapplicatie in te stellen. Mocht je op je website meerdere webapplicaties willen draaien, dan houdt de virtualenv de context gescheiden. Zo hoef je je niet druk te maken als verschillende apps verschillende versies van Python of van pakketten nodig hebben – dit blijft netjes gescheiden.
Django installeren
Hoewel er alternatieve opties zijn om met je eigen webapplicatie verder te gaan (from scratch, met Flask of Web2py), ga ik voor deze demo-applicatie uit van Django. Nadat je via SSH je virtualenv hebt geactiveerd, kun je eenvoudig starten met Django door met pip de benodigde pakketten te installeren.
pip install --upgrade pip
pip install django mysqlclient
Vervolgens maak je met het onderstaande django-admin-commando je project aan in de huidige map. Merk op dat de spatie en punt achter ‘demo’ essentieel zijn. Laat je dit achterwege, dan komt het hele project één map te diep te staan. Je raakt dan hierna in de knoop met dit stappenplan.
django-admin startproject demo .
Configuratie
Een paar aanpassingen in het bestand demo/settings.py helpen je op weg met de databaseverbinding en de logging. Merk op dat een wijziging in settings.py pas actief wordt na een herstart van de applicatie. De webapplicatie herstarten, kan in de Python-selector.
Voeg nu je website-URL toe aan ALLOWED_HOSTS om Django-verzoeken naar deze URL te laten accepteren. De debug modus zetten we uit, omdat het veiliger is om foutmeldingen op de server te loggen. Zonder debug modus worden statische bestanden (CSS/JS) ook op een slimmere manier geserveerd.
ALLOWED_HOSTS = [‘<example.com>']
DEBUG = False
STATIC_ROOT = '/home/<deb12345>/domains/<example.com>/public_html/static'
De toevoeging van de STATIC_ROOT-instelling laat Django weten waar de statische bestanden uit de webapplicatie terecht moeten komen. Vergeet niet de gebruikersnaam en het domein te vervangen door je eigen gegevens.
Om fouten in de webapplicatie op te sporen, wil je dat Django naar een bestand kan loggen. Voeg hiervoor het volgende blok code toe. Vervang de gegevens bij ‘filename’ met je eigen gebruikersnaam en locatie.
LOGGING = {
'version': 1,
'disable_existing_loggers': False,
'handlers': {
'file': {
'level': 'INFO',
'class': 'logging.FileHandler',
'filename': '/home/<deb12345>/django.log',
},
},
'loggers': {
'django': {
'handlers': ['file'],
'level': 'INFO',
'propagate': True,
},
},
}
De gegevens van je Django-applicatie worden standaard opgeslagen in een SQLite-database (db.sqlite3). Gebruik je liever een MySQL-database? Vervang dan het blok DATABASES met onderstaande code. Vul tussen de quotes je eigen MySQL-gegevens in.
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.mysql',
'NAME': '<database_naam>',
'USER': '<database_gebruiker>',
'PASSWORD': '<database_wachtwoord>',
'HOST': 'localhost',
'PORT': '3306',
}
}
Je eerste testpagina toevoegen
Om te kunnen testen of de webapplicatie naar behoren werkt, maken we een hello-world-testpagina. Start hiervoor een nieuwe app binnen je project met:
python manage.py startapp begin
Dit maakt een nieuwe map ‘begin’ aan, een submodule waarin je de view voor je testpagina kunt toevoegen. Vervang hiervoor de inhoud van begin/views.py met de view-functie voor de testpagina:
from django.http import HttpResponse
def index(request):
return HttpResponse("Hallo wereld, je testpagina werkt!")
Zorg dat de URL’s uit je app ‘begin’ worden ingeladen door de hoofdapplicatie met de volgende code in demo/urls.py:
from django.contrib import admin
from django.urls import path
from begin.views import index
urlpatterns = [
path('', index),
path('admin/', admin.site.urls),
]
Als laatste wil je in settings.py de nieuwe module toevoegen in de lijst van INSTALLED_APPS (gewoon de string ‘begin’, zonder ‘django.contrib’).
Voorbereiding op livegang
Je hebt de code voor de testpagina nu klaar! Er zijn een paar voorbereidende stappen die nog handig zijn om uit te voeren, voor je aan de slag gaat met je Django-applicatie. Gebruik het commando uit de Python-selector om je virtualenv te activeren en in de juiste projectmap te komen. Vervolgens kun je met het manage.py-script van Django je webapplicatie klaarmaken voor gebruik.
python manage.py collectstatic
python manage.py migrate
python manage.py createsuperuser
In Django zit een standaard admin-gedeelte, waarmee je eenvoudig de gegevens in je database kunt onderhouden.
- Met ‘collectstatic’ zet je de CSS- en JavaScript-bestanden klaar in public_html (zoals aangegeven in de waarde STATIC_ROOT).
- Met ‘migrate’ maak je de initiële databasestructuur aan die nodig is voor de Django admin.
- Met ‘createsuperuser’ maak je een beheeraccount aan voor de admin pagina. Gebruik een sterk wachtwoord.
Je webapplicatie activeren
Je Django-applicatie is klaar voor gebruik, maar de Python-selector weet nog niet hoe het de webapplicatie kan inladen. Hiervoor navigeer je terug naar de Python-selector en vervang je de waarde bij ‘Application startup file’. Dit was voorheen passenger_wsgi.py en wordt in ons geval nu demo/wsgi.py. Sla op met ‘Save’ en klik op ‘Restart’ om alle wijzigingen door te voeren.
Testen en vervolg
Gefeliciteerd! Als alles goed gelukt is, dan zie je nu op jouw domeinnaam de volgende testpagina.
Ook moet het admingedeelte van Django beschikbaar zijn.
Wil je meer info over het installeren en uitbreiden van een Django-applicatie, volg dan de officiële tutorial van het Django-project.
Mogelijke foutmeldingen en oplossingen
Loop je vast bij de aanmaken van je Python-webapplicatie, bekijk dan eerst deze veelvoorkomende foutmeldingen en oplossingen daarvoor.
403 forbidden
Controleer in de Python-selector of je webapplicatie draait en of de juiste wsgi.py staat ingesteld.
404 not found
Controleer het subpath in de Python-selector met de URL die je gebruikt. Check of die instellingen overeenkomen met het voorbeeld en of je de wsgi.py uit je Django-project goed hebt ingesteld onder ‘Application startup file’. Controleer verder de urls.py in ‘demo’ en ‘begin’ om te zien of de index view onder de juiste URL is gekoppeld (een lege string, geen slash). Vergeet de app niet te restarten na eventuele wijzigingen in deze bestanden.
500 Internal Server Error
Zie je geen beginpagina, maar een foutpagina? Kijk dan in de django.log of start de server handmatig in SSH om te zien waar de fout zit:
python ./manage.py runserver
Can’t acquire lock for app: <applicatienaam>
Het kan gebeuren dat in DirectAdmin de pagina herladen of gesloten wordt tijdens het uitvoeren van een commando of wijziging in de Python-selector. Er kan dan er een lockfile achterblijven, het bestand dat DirectAdmin normaal gesproken gebruikt om te voorkomen dat er twee acties door elkaar lopen. Wacht een paar minuten en als je zeker weet dat er geen acties meer lopen, dan kun je de lockfile via SSH verwijderen. Deze is te vinden in:
virtualenv/<applicatienaam>/.lock
Django admin heeft geen styling
Als de Django admin er niet zo uitziet als in het voorbeeld, ga dan na of de static-map in je public_html is gevuld met bestanden voor de admin-module. Mochten deze ontbreken, bekijk dan de STATIC_ROOT-instelling. Controleer of STATIC_URL verwijst naar de juiste static-map en draai het volgende commando opnieuw:
python manage.py collectstatic
P.S. Blijf op de hoogte en volg ons via Facebook, Twitter, Instagram, e-mail en RSS. Heb je vragen, tips of opmerkingen? Laat het achter als reactie. Vond je het artikel nuttig? Deel het dan met anderen!
Geweldig nieuws! Ik zat al een tijd te zoeken naar een nieuwe host omdat ik steeds meer met Python doe, maar eigenlijk wou ik helemaal niet weg bij Antagonist. Fijn dat ik nu het beste van beide werelden kan gebruiken!
Heel tof. Bedankt voor je enthousiaste reactie, Sebastiaan! 🙂
Hoi jonathan, complimenten voor deze uitbreiding. Ik was zelf al plm 2 maanden geleden aan de slag gegaan en had een django app draaiend gekregen die ik als api gebruik. Op 18 juni exact werkte hij niet meer, wat jullie ongetwijfeld via mijn mail aan de helpdesk te weten zijn gekomen.
Omdat verder niets lukte heb ik de hele app maar verwijderd en ben opnieuw begonnen. Toen ook dat een fout bleef geven heb ik slaafs je voorbeeld gevolgd en een demo app gemaakt zoals beschreven. Waar ik nu achter ben is het volgende: je kan de app niet in een folder op een niveau dieper installeren, zoals ik aanvankelijk gedaan had, en wat toen werkte. Het zat bij mij in : naam1/naam2/ in de virtual env. Waarschijnlijk worden zodoende paden niet gevonden. Ik heb alles nu direct in de hoofdfolder gezet, en via de url toch weer het path op naam1/naam2/ kunnen zetten. Ik heb nu gelukkig weer een django die reageert. Nu nog alles verder werkend krijgen. Ook gaat er bij het installeren van de mysql client nog iets fout, wat een algemeen probleem is: eerst moet pip geupdated worden van vs 9 naar vs 20. Dat kan via pip install –upgrade pip. Wellicht handig om dit in de tutorial te vermelden.
Groeten, Robert
Bedankt voor de nuttige feedback, Robert! We hebben op basis daarvan een aantal aanpassingen aan het artikel doorgevoerd.
Super fijn dat dit toegevoegd is! Heel nuttig. Dank. Dank. Dank.
Graag gedaan, Jasper. Fijn dat je er wat aan hebt, erg bedankt voor je toffe feedback!
Super! Heel blij mee 🙂
Fijn om te lezen, Joris!
Verrassend en tegelijkertijd geweldig nieuws !
Vorig jaar al de vraag neergelegd bij Antagonist of er de mogelijkheid bestond om Python te draaien ….. ben erg blij dat hiernaar geluisterd is (zal vast niet de enige zijn geweest) en er nu ook de mogelijkheid bestaat om dit te gebruiken.
Zelf gebruik ik al een aantal jaar web2py. Zou mooi zijn als ook hiervoor een korte instructie komt hoe dit in te richten.
Goed gedaan
Bedankt voor je feedback, Stefan. Tof dat je er wat aan hebt! Het uitrollen van een Python-applicatie kan bij ons meestal, zoals je het ook gewend bent van andere platforms. De wens voor een Web2py-handleiding staat in ieder geval genoteerd. Mocht je daar trouwens erg thuis in zijn en vind je het leuk om er de basis voor aan te leveren, dan kan zo’n handleiding ook gezamenlijk tot stand komen. Deze info is verder wellicht nuttig voor nu: http://web2py.com/books/default/chapter/29/13/deployment-recipes#anyserver-py
Python lukt. Tof. Erg blij mee. Nu Flask nog. Kan dat en zo ja, hoe? Alvast dank.
Goed om te horen dat je positieve ervaringen hebt met Python, Victor! We ondersteunen Python-applicaties met Flask op onze hostingservers. Momenteel hebben we hier nog geen handleiding voor, maar ik heb de wens voor je genoteerd. Bedankt voor de feedback!
Weer een stap verder. Flask draait nu, maar nog heel veel vragen blijven overeind. Zoals: waar ligt het bestand om de website te bewerken? Ik heb passenger_wsgi.py gevonden en bewerkt… maar de output blijft hetzelfde.
Fijn dat Flask al draait, Victor! Heb je een app.py aangemaakt voor de Flask-code en deze in de wsgi ingeladen door de inhoud van passenger_wsgi.py te vervangen met:
from app import app as application
Vervolgens moet je app.py verder kunnen uitbreiden. Overigens zijn we momenteel bezig met een blog over webapplicaties maken met Flask. Deze verschijnt binnenkort online. We verwachten dat die veel van je vragen zal wegnemen.
RTFM: Na heel wat gefrustreerd gedoe in het begin (meteen een Django app werkend krijgen aan de hand van bovenstaande – uitstekende – handleiding, ben ik maar eens eerst begonnen met handleidingen over Django, en daarna weer ‘hier’ verder gegaan. Het werkt als een tierelier.
Superfijn dat ik geen gebruik hoef te maken van Heroku, Digital Ocean, Azure of AWS.
Sowieso fijn dat we toegang hebben met SSH zodat ook een Laravel project opgezet kan worden.
Ik hoop dat deze Python/Node selectors een blijvertje zijn!
Bedankt voor je reactie en het delen van je ervaring. Fijn om te lezen dat je eruit bent gekomen en het nu als een tierelier werkt!
Instructie exact gevolgd met exact dezelfde waardes (dus 1 op 1 wat hier staat) om te testen (dus met demo voor applicatie etc) , maar bij het commando (in SSH dus en na activeren virtualenv):
pip install django “mysqlclient<2.0.2"
Krijg ik al de foutmelding in prachtig rood:
ERROR: Could not build wheels for mysqlclient, which is required to install pyproject.toml-based projects
Volgens stackoverflow zou dit te maken hebben met een missende library op de server?
Hi Ramon, ons eerste vermoeden was dat de package te oud was. Voor de zekerheid hebben we daarom nogmaals exact de stappen nagelopen. Echter, we lopen daarbij niet tegen de door jou genoemde foutmelding aan. Desalniettemin is het beter om een moderne versie te installeren. Dit doe je met pip install django mysqlclient. We hebben die stap in het artikel geüpdatet. Zou je het nogmaals van vooraf aan willen proberen en kijken of het nu wel lukt?
Het is nu gelukt. Bedankt voor de snelle response , leuk om te doen. Mijn Django ‘hello world’ demo installatie, draait inmiddels op https:///demo. Zeer enthousiast nu om verder te gaan met Python en Node mogelijkheden bij Antagonist.
Top, fijn om te lezen dat het nu is gelukt en je enthousiast bent om verder te gaan. Veel succes!