Rango hat geschrieben: ↑Mittwoch 28. Juli 2021, 15:56
YAPD hat geschrieben: ↑Mittwoch 28. Juli 2021, 15:48
Du könntest es natürlich auch so anlegen, dass ein Objekt - Manager die jeweiligen Module lädt.
Das hätte den Vorteil, dass du im Modul "XY" z.B. automatisch auf Dateien im "plugins" Ordner
suchen könntest und die Daten sind variabel ladbar, da er neue Dateien automatisch verarbeitet.
Beste Grüße
YAPD
Könntest du das bitte noch etwas näher ausführen?
Hi,
ja natürlich kann ich das noch ausführlicher beschreiben
Als erstes importierst du 'importlib'
Dann erstellst du eine Datei, z.B. "ObjectManager.pm" , der du eine Klasse gibst,
in diesem Fall "OM".
Wichtig für die richtige Ablage der Objekte ist, dass du direkt im "Kopf" der Klasse
das Dictionary "OM_Objects" anlegst.
Code: Alles auswählen
class OM:
OM_Objects = { }
def __init__( self ):
print( "Initialisierung des OM !" )
Nun definierst du in der Klasse "OM" zwei Sub - Routinen, Load & Builder :
Load :
Code: Alles auswählen
def Load( Self , Module = "" ) :
if Module == "" :
print( "WARNING : No Module Specified !" )
return
if Module in OM.OM_Objects.keys( ) :
print( "INFO : The Specified Module '" + Module + "' Is Already Loaded !" )
return OM.OM_Objects[ Module ]
OBJ = OM.Builder( Self , Module )
return OBJ
Dies ist der Aufruf des gewünschten Objekts. Er prüft, ob das Objekt bereits in OM.OM_Objects vorhanden
ist. Wenn dies der Fall ist, gibt es das vorhandene Objekt zurück ( return OM.OM_Objects[ Module ] ).
Andersfall ruft er den Builder mit dem Modul als Parameter auf.
Builder :
Code: Alles auswählen
def Builder( Self , Module ):
OM_Package = Module
OM_FH = Module
OM_FH = OM_FH.replace('::', "\\" )
OM_FH = OM_FH + ".py"
OM_FH_Status = os.path.exists( os.getcwd( ) + "\\" + OM_FH )
if OM_FH_Status == False :
print( "[ ERROR ] The Specified Module '" + Module + "' Is Not Available !" )
return
OM_Class = OM_Package
OM_Class_Seperator = OM_Class.count( "::" )
OM_Class = OM_Class.split( "::" , OM_Class_Seperator )
OM_UID = OM_Class[ OM_Class_Seperator ]
OM_Package = OM_Package.replace( '::' , "." )
OM_Module_Instance = importlib.import_module( OM_Package )
OM_Object_Methods = [ method_name for method_name in dir( OM_Module_Instance )
if callable(getattr( OM_Module_Instance , method_name ) ) ]
if OM_UID not in OM_Object_Methods :
print( "[ ERROR ] The Constructor For Module '" + Module + "' Could Not Be Found !" )
return
OM_OBJ = getattr( OM_Module_Instance , OM_UID )( )
OM.OM_Objects.update( { Module : OM_OBJ } )
return OM.OM_Objects[ Module ]
Der Code des Loaders prüft die Existenz der Datei ( OM_FH_Status = os.path.exists( os.getcwd( ) + "\\" + OM_FH ) )
und wandelt den Namen des Moduls, das geladen werden soll, um, so dass es erkannt wird :
HINWEIS : Ich habe das Script so geschrieben, dass man ein Modul mit folgendem Befehl lädt :
test = OM( )
result1 = test.Load( "Config" ) -------> Lädt Dateien aus dem Hauptverzeichnis
result1 = test.Load( "Kernel::Testumgebung" ) -------> Lädt Dateien aus einem Unterverzeichnis, indem er
den Namen konvertiert ( OM_Package = OM_Package.replace( '::' , "." ) )
Anschließend initialisiert er das Modul mit dem Befehl : OM_Module_Instance = importlib.import_module( OM_Package )
Code: Alles auswählen
OM_Object_Methods = [ method_name for method_name in dir( OM_Module_Instance )
if callable(getattr( OM_Module_Instance , method_name ) ) ]
Damit alle Module korrekt verarbeitet werden, entspricht der 1. Klassenamen immer dem Dateinamen,
also z.B. in der "Config.py ---> class Config:" , in der "Testumgebung.py -----> class Testumgebung:" usw.
Vorher hat die Builder Funktion mit :
Code: Alles auswählen
OM_Class_Seperator = OM_Class.count( "::" )
OM_Class = OM_Class.split( "::" , OM_Class_Seperator )
OM_UID = OM_Class[ OM_Class_Seperator ]
den Namen des Moduls ermittelt. Damit ruft es nun die o. g. Klasse auf :
Nachdem das Objekt der Klasse initialisiert wurde, schreiben wir es mit
noch in das Dictionary OM.OM_Objects und geben das Objekt zurück an die "Load()" Funktion,
die wiederum das Objekt zurückgibt.
Dadurch erhältst du mit
das Objekt zurück und kannst bequerm auf die Werte zugreifen, z.B. :
String -> result1.String
Dictionary -> result1.Dictionary[ "Test" ]
Und natürlich kann man auch andere Subs aufrufen, z B. :
result1.Testumgebung( )
Puh, das war dann doch einiges an Text. Sorry, dass es länger gedauert hat
Beste Grüße
YAPD