[gelöst?] Neuling mit Konzeptfrage

Sockets, TCP/IP, (XML-)RPC und ähnliche Themen gehören in dieses Forum
Antworten
Sanji
User
Beiträge: 12
Registriert: Donnerstag 17. August 2006, 15:32
Kontaktdaten:

Hallo,

ich habe in den letzten Jahren einige Websites in PHP aufgebaut und möchte jetzt meine eigene Seite auf Python umstellen. Da ich eine Abscheu vor externen Template-Systemen oder solchen aufgeblähten Konstruktionen, möchte ich diese auch nicht einsetzen.

Mein großes Problem ist die Verteilung meiner Scripts auf mehrere Dateien. Bei meinem Hoster läuft mod_python mit Python 2.4.3. Soweit ich mich belesen habe, werden ja quasi alle .py-Anfragen zum PythonHandler weitergeleitet, der die Anfrage dann behandelt.

In dieser Datei (nennen wir sie mal handler.py) dachte ich mir jetzt, dass ich schaue, welche Datei eigentlich aufgerufen wurde (sagen wir mal index.py) und diese dann einbinde, um sie auszuführen. Leider hat keiner der hier geposteten Lösungen (__import__, eval("import...")) funktioniert. Dummerweise läuft der Python Interpreter im PythonRoot und findet daher nicht so einfach meine Scripts in meinem DocumentRoot.

Was kann ich denn tun, um in meiner handler.py die "index.py" aus dem gleichen Verzeichnis, in dem auch die handler.py liegt, einzubinden und auszuführen?

Grüße,
Christoph
Zuletzt geändert von Sanji am Mittwoch 20. Dezember 2006, 17:07, insgesamt 1-mal geändert.
EnTeQuAk
User
Beiträge: 986
Registriert: Freitag 21. Juli 2006, 15:03
Wohnort: Berlin
Kontaktdaten:

Wenn deine Scripte mit mod_python ausgeführt werden und nicht im System-Pfad - also z.B. in den site-pakages liegen musst du die Option

Code: Alles auswählen

PythonPath "['pfad/zum/script'] + sys,path"
.

Ich habe deine Frage zwar nicht ganz verstanden aber eins kann ich dir sagen. Wenn du Scripte mit mod_python ausführen möchtest benötigst du einen mod_python handler oder ein mod_python GateWay - was was ist.... da suche ich noch --

Als Beispiel sei mal http://trac.pocoo.org/repos/modpywsgi/modpywsgi.py
erwähnt.
Dieses binde ich bei mir in folgender Apache-Config ( httpd.conf )ein:

Code: Alles auswählen

        <Location />
                AddHandler mod_python .py
                PythonHandler modpywsgi::handler
                PythonAutoReload On
                PythonPath "['/home/ente/entes-world'] + sys.path"
                PythonOption application index::app
                PythonDebug On
        </Location>
Solltest du keinen Zugriff auf die httpd.conf haben dann sollte es reichen die Einstellungen in eine .htaccess reinzuschreiben.

MfG EnTeQuAk
Sanji
User
Beiträge: 12
Registriert: Donnerstag 17. August 2006, 15:32
Kontaktdaten:

Mein Problem ist ja, dass alle Anfragen auf .py-Dateien zum Handler geleitet werden. Und der soll jetzt entscheiden, welche Datei denn eigentlich angefordert wurde (über req.filename) und diese dann einbinden, um sie auszuführen. Aber ich schaffe es nicht, Dateien in meinem docroot einbinden zu lassen. Ich habe folgenden Code:

Code: Alles auswählen

##############################
# handler.py - mein PythonHandler

from mod_python import apache
import os, sys

ROOT_DIR = "G:\\docroot\\example.com\\wwwpy"

def handler(req):
	req.content_type = "text/plain"
	req.send_http_header()
	req.write(os.path.basename(req.filename)+" wurde aufgerufen.\n\n")
	from bob import bobfunc
	
	bobfunc(req,5)
	
	return apache.OK

##############################
# bob.py im DocumentRoot (dort, wo auch die handler.py liegt)

# -*- coding: iso-8859-15 -*-

def bobfunc(req,n):
	req.write("foo "+n)
Und zusätzlich in der .htaccess im DocumentRoot:

Code: Alles auswählen

PythonPath "['G:\\docroot\\example.com\\wwwpy'] + sys.path"
Bei einem Aufruf von http://localpy/bob.py (localpy ist ein virtueller Host auf 127.0.0.1) erhalte ich dann im Browser die Ausgabe:
bob.py wurde aufgerufen.


<pre>
Mod_python error: "PythonHandler handler"

Traceback (most recent call last):

File "G:\Software\Python-2.4.4\Lib\site-packages\mod_python\apache.py", line 299, in HandlerDispatch
result = object(req)

File "G:\docroot\example.com\wwwpy\handler.py", line 10, in handler
from bob import bobfunc

ImportError: cannot import name bobfunc

</pre>
Benutzeravatar
jens
Python-Forum Veteran
Beiträge: 8502
Registriert: Dienstag 10. August 2004, 09:40
Wohnort: duisburg
Kontaktdaten:

Sanji hat geschrieben:Da ich eine Abscheu vor externen Template-Systemen oder solchen aufgeblähten Konstruktionen, möchte ich diese auch nicht einsetzen.
Also ich kann dir nur jinja empfehlen. Ist eine wirklich einfache schlanke Template-Sprache: http://wsgiarea.pocoo.org/jinja/

GitHub | Open HUB | Xing | Linked in
Bitcoins to: 1JEgSQepxGjdprNedC9tXQWLpS424AL8cd
EnTeQuAk
User
Beiträge: 986
Registriert: Freitag 21. Juli 2006, 15:03
Wohnort: Berlin
Kontaktdaten:

Ach ja...

@ Sanji:

Sorry hier bin ich auch gerade am basteln... ich probiere zwar erstmal andere Handler aus... aber so richtig will das alles nicht.

Daher werde ich mir für PyLucid wohl oder übel auch einen basteln müssen,.,.. *grml*

Nun ja... solltest du da etwas schönes hinbekommen :) Bin ich immer erfreut :)

MfG EnTeQuAk
Sanji
User
Beiträge: 12
Registriert: Donnerstag 17. August 2006, 15:32
Kontaktdaten:

Also ich habe jetzt noch ein wenig rumprobiert und die einzige Lösung, die ich gefunden habe, ist, das gewünschte Script von der handler.py per execfile() ausführen zu lassen. Die Datei, die dann ausgeführt wird (bei mir bob.py) hat dann "global" das ApacheRequest-Objekt und dann damit ganz normal agieren.

Stellt sich mir nur die Frage, ob das Performance-Probleme geben könnte.
Sanji
User
Beiträge: 12
Registriert: Donnerstag 17. August 2006, 15:32
Kontaktdaten:

Also meine handler.py sieht jetzt so aus:

Code: Alles auswählen

# -*- coding: iso-8859-1 -*-

from mod_python import apache
import os, sys

ROOT_DIR = "G:\\docroot\\example.com\\wwwpy\\" #der DocRoot

def handler(req):
	req.content_type = "text/html"
	req.send_http_header()
	
	file = os.path.basename(req.filename)
	
	if not os.path.exists(ROOT_DIR+file) or file == "handler.py":
		req.status = apache.HTTP_NOT_FOUND
		req.write("Oh, das ging schief (404).")
		return apache.OK
	
	execfile(ROOT_DIR+os.path.basename(req.filename))
	
	return apache.OK
Der Handler rendert seine eigene 404-Seite, wenn eine nicht existente Datei oder der Handler selbst aufgerufen wurde. Ansonsten führt es die Datei aus, die aufgerufen wurde (req.filename). Läuft wunderbar. :) Dann kann ich mich jetzt daran machen, im Laufe der nächsten 12 Monate meine ganze Website langsam umzucoden.

Edit (Leonidas): Highlighting eingeschaltet.
Benutzeravatar
jens
Python-Forum Veteran
Beiträge: 8502
Registriert: Dienstag 10. August 2004, 09:40
Wohnort: duisburg
Kontaktdaten:


GitHub | Open HUB | Xing | Linked in
Bitcoins to: 1JEgSQepxGjdprNedC9tXQWLpS424AL8cd
Antworten