Seite 1 von 1
Module aus höheren Verzeichnisebenen benutzen
Verfasst: Dienstag 14. Oktober 2008, 11:18
von andilar
Hallo Zusammen,
wenn ich ein Modul habe ähnlich diesem hier:
Code: Alles auswählen
class my_module_library(object):
def __init__(self):
print 'my_module_lib'
def another_method(self):
print 'another method'
dann kann ich das Modul sofern ich in dem gleichen Verzeichnis bin in einem anderen Modul doch so benutzen:
Code: Alles auswählen
import my_module_lib
my_module_lib.my_module_library().another_method()
Ob das nun guter Stil ist oder ähnliches spielt keine Rolle, da ich hier an Vorgaben gebunden bin. Die Syntax des zweiten Teils soll genauso aussehen wie geschrieben.
Jetzt ist es so das ich 2 Etagen tiefer in dem Verzeichnisbaum die selbe Syntax zur Verfügung stellen möchte. Soweit mein python Wissen reicht, kann ich einen
import eines selbstgeschrieben Moduls in der Form aber nur durchführen, wenn ich mich im gleichen Verzeichnis befinde. Nun scheint es nicht sehr sinnvoll in alle Verzeichnisse die benötigten Module zu kopieren.
Irgendwo habe ich gesehen das man auch einen Pfad importieren kann. Das ist aber ebenfalls nicht erwünscht, da der Pfad sich entsprechend dem Verzeichnis in dem man das Modul nutzen möchte ändert.
Gibt es eine Möglichkeit für die Laufzeit des Programms ein Modul in den Pythonpfad einzutragen so das es überall per
import mein_modul erreichbar ist? Wie macht man das sonst?
Ich bin an python 2.2.1 und winXP gebunden...
Eine anderer Lösungsansatz wäre auch in Ordnung, danke.
Verfasst: Dienstag 14. Oktober 2008, 11:46
von Y0Gi
Hey,
innerhalb deiner Anwendung solltest du Module stets über den absoluten Pfad importieren, also etwa
Code: Alles auswählen
from someapplication.core import somemodule
somemodule.SomeClass().some_method()
Damit bist du unabhängig vom Ausführungszeichnis, solange die Applikation selbst sich im Pfad befindet.
Der Pfad lässt sich über die Umgebungsvariable ``PYTHONPATH`` festlegen, zumindest unter Unix. Unter Windows gilt das IIRC allerdings ebenso. Im Code (etwa des Moduls/Scripts, das man zum Starten der Anwendung verwendet) kann man z. B. explizit den übergeordneten Pfad wie folgt eintragen:
Code: Alles auswählen
import sys
sys.path.append('..')
# bzw.
sys.path.insert(0, '..')
An welcher Stelle man den Pfad in die Liste der zu durchsuchenden Pfade einfügt wird bei Überschneidungen von Modul- oder Paketnamen interessant.
Um Überschneidungen durch Modul- oder (Unter-)Paketnamen mit der Standardbibliothek zu vermeiden (etwa ``someapplication.string``) sollte man o. g. absolute Imports benutzen.
andilar hat geschrieben:Irgendwo habe ich gesehen das man auch einen Pfad importieren kann. Das ist aber ebenfalls nicht erwünscht, da der Pfad sich entsprechend dem Verzeichnis in dem man das Modul nutzen möchte ändert.
Kannst du das näher ausführen? Hört sich für mich nicht auf Anhieb nach einer guten Idee an.
Verfasst: Dienstag 14. Oktober 2008, 12:24
von andilar
Meun Y0Gi,
Y0Gi hat geschrieben:
andilar hat geschrieben:Irgendwo habe ich gesehen das man auch einen Pfad importieren kann. Das ist aber ebenfalls nicht erwünscht, da der Pfad sich entsprechend dem Verzeichnis in dem man das Modul nutzen möchte ändert.
Kannst du das näher ausführen? Hört sich für mich nicht auf Anhieb nach einer guten Idee an.
Das war die Geschichte mit dem:
was ich in jedem Modul mit einem anderen angepassten Pfad benutzt hätte und natürlich ekelig aussieht, ohne Frage.
Deinen Ansatz schaue ich mir mal genauer an. Irgendwie habe ich das Gefühl das es für mich noch ein Geheimnis gibt in Richtung python und Anwendungen daraus bauen.
Y0Gi hat geschrieben:innerhalb deiner Anwendung solltest du Module stets über den absoluten Pfad importieren, also etwa
Code: Alles auswählen
from someapplication.core import somemodule
somemodule.SomeClass().some_method()
Damit bist du unabhängig vom Ausführungszeichnis, solange die Applikation selbst sich im Pfad befindet.
Der Pfad lässt sich über die Umgebungsvariable ``PYTHONPATH`` festlegen, zumindest unter Unix. Unter Windows gilt das IIRC allerdings ebenso. Im Code (etwa des Moduls/Scripts, das man zum Starten der Anwendung verwendet) kann man z. B. explizit den übergeordneten Pfad wie folgt eintragen:
Code: Alles auswählen
import sys
sys.path.append('..')
# bzw.
sys.path.insert(0, '..')
An welcher Stelle man den Pfad in die Liste der zu durchsuchenden Pfade einfügt wird bei Überschneidungen von Modul- oder Paketnamen interessant.
Um Überschneidungen durch Modul- oder (Unter-)Paketnamen mit der Standardbibliothek zu vermeiden (etwa ``someapplication.string``) sollte man o. g. absolute Imports benutzen.
Dennoch glaube ich das ich in jedem Modul in den Unterverzeichnissen einen anderen Pfad angeben müsste der zu importieren gilt.
Vielleicht noch etwas ausführlicher zu dem Problem:
Es werden von einem angegeben Verzeichnis ausgehend alle Unterverzeichnisse aufgerufen und nach python Modulen durchsucht. Die gefundenen Module sollen anschließend der Reihe nach ausgeführt werden.
Jedes Modul benutzt bei der Ausführung die selben Basismodule mit bestimmten Methoden. Natürlich sollte nicht in jedem Verzeichnis das Basismodul liegen.
Die Anzahl oder die Art der Verschachtelung der Unterverzeichnisse soll auch vollkommen unabhängig von dem obersten Verzeichnis sein.
Vielleicht habe ich da was nicht so richtig verstanden, aber ich möchte die import Anweisung immer gleich lautend haben und nicht je nach Verzeichnisstruktur ändern.
Das ist natürlich irgendwie seltsam, aber eine Anforderung an mein Tool. :/
Verfasst: Dienstag 14. Oktober 2008, 12:58
von BlackJack
Die Frage ist halt, wie sehr man Pythons Import-Mechanismus verbiegen muss um Deine Anforderungen zu erfüllen, oder ob man sich das mit den Anforderungen nicht noch einmal überlegen sollte. Du kämpfst hier ein bisschen gegen die Sprache.
Verfasst: Dienstag 14. Oktober 2008, 14:16
von andilar
Ja mein Mund ist auch schon ganz fusselig...
Es sollte aber mit dem
sys.path.append('..') und etwas umschreiben der Anforderung doch ganz gut funktionieren.
Vielen Dank
Verfasst: Dienstag 14. Oktober 2008, 20:56
von name
Verfasst: Dienstag 14. Oktober 2008, 22:18
von andilar
Ja wie cool, du kannst dir nicht vorstellen wie gerne ich python 2.5 hätte. Das entpricht genau meinem Problem.
Gut zu wissen falls ich nicht mehr an 2.2.1 gebunden bin, danke.
Verfasst: Mittwoch 15. Oktober 2008, 07:14
von birkenfeld
Erstens ist "import ..foo" ein SyntaxError, zweitens funktioniert "from .. import foo" auch ohne Future-Import, und drittens funktioniert das ganze nur, wenn "foo" im selben Package ist wie das importierende Modul, was die Nützlichkeit der Sache für den OP schon ein wenig einschränkt...
Verfasst: Mittwoch 15. Oktober 2008, 10:15
von lunar
Wenn das so eine Art Plugin-Mechanismus werden soll, dann wäre wohl eher ein Blick auf "imp"-Modul anzuraten anstatt wild sys.path zu verbiegen.
Verfasst: Mittwoch 15. Oktober 2008, 14:49
von name
birkenfeld hat geschrieben:
Erstens ist "import ..foo" ein SyntaxError, zweitens funktioniert "from .. import foo" auch ohne Future-Import, und drittens funktioniert das ganze nur, wenn "foo" im selben Package ist wie das importierende Modul, was die Nützlichkeit der Sache für den OP schon ein wenig einschränkt...
Hoppla, stimmt. Gestern war nicht so mein Tag, ich sollte mehr schlafen