213 Stimmen

Aufbau einer minimalen Plugin-Architektur in Python

Ich habe eine in Python geschriebene Anwendung, die von einer eher technischen Zielgruppe (Wissenschaftler) genutzt wird.

Ich suche nach einer guten Möglichkeit, die Anwendung durch die Benutzer erweiterbar zu machen, d.h. eine Skripting/Plugin-Architektur.

Ich bin auf der Suche nach etwas extrem leicht . Die meisten Skripte oder Plugins werden nicht von einem Drittanbieter entwickelt, vertrieben und installiert, sondern sind etwas, das ein Benutzer in wenigen Minuten erstellt, um eine sich wiederholende Aufgabe zu automatisieren, ein Dateiformat zu unterstützen usw. Plugins sollten also ein absolutes Minimum an Boilerplate-Code haben und keine andere "Installation" erfordern als das Kopieren in einen Ordner (so etwas wie setuptools-Einstiegspunkte oder die Zope-Plugin-Architektur scheint zu viel zu sein).

Gibt es bereits solche Systeme oder Projekte, die ein ähnliches Schema implementieren, die ich mir ansehen sollte, um Ideen und Anregungen zu erhalten?

11voto

edomaur Punkte 1389

Marty Allchin's einfaches Plugin-Framework ist die Basis, die ich für meinen eigenen Bedarf verwende. Ich empfehle wirklich, einen Blick darauf zu werfen, ich denke, es ist wirklich ein guter Anfang, wenn man etwas einfaches und leicht hackbares will. Sie können es auch finden als Django-Schnipsel .

10voto

guneysus Punkte 5747

Wenn ich auf der Suche nach Python Dekorateure, fand eine einfache, aber nützliche Code-Schnipsel. Es kann nicht in Ihre Bedürfnisse passen, aber sehr inspirierend.

Scipy Fortgeschrittenes Python#Plugin Registrierungssystem

class TextProcessor(object):
    PLUGINS = []

    def process(self, text, plugins=()):
        if plugins is ():
            for plugin in self.PLUGINS:
                text = plugin().process(text)
        else:
            for plugin in plugins:
                text = plugin().process(text)
        return text

    @classmethod
    def plugin(cls, plugin):
        cls.PLUGINS.append(plugin)
        return plugin

@TextProcessor.plugin
class CleanMarkdownBolds(object):
    def process(self, text):
        return text.replace('**', '')

Verwendung:

processor = TextProcessor()
processed = processor.process(text="**foo bar**", plugins=(CleanMarkdownBolds, ))
processed = processor.process(text="**foo bar**")

8voto

Jon Mills Punkte 1715

Mir hat die nette Diskussion über verschiedene Plugin-Architekturen von Dr. Andre Roberge auf der Pycon 2009 gefallen. Er gibt einen guten Überblick über verschiedene Möglichkeiten der Implementierung von Plugins, ausgehend von etwas wirklich Einfachem.

Es ist erhältlich als podcast (zweiter Teil nach einer Erklärung von monkey-Parcheando), begleitet von einer Reihe von sechs Blogeinträge .

Ich empfehle Ihnen, kurz hineinzuhören, bevor Sie eine Entscheidung treffen.

5voto

samwyse Punkte 2470

Ich kam hierher, um nach einer minimalen Plugin-Architektur zu suchen, und fand eine Menge Dinge, die mir allesamt als Overkill erschienen. Also, ich habe implementiert Supereinfache Python-Plugins . Um es zu verwenden, erstellen Sie ein oder mehrere Verzeichnisse und legen eine spezielle __init__.py in jeder Datei. Der Import dieser Verzeichnisse führt dazu, dass alle anderen Python-Dateien als Submodule geladen werden, und ihr(e) Name(n) wird(werden) in der Datei __all__ Liste. Dann liegt es an Ihnen, diese Module zu validieren/initialisieren/registrieren. In der README-Datei finden Sie ein Beispiel.

4voto

ankostis Punkte 7409

Eigentlich setuptools arbeitet mit einem "Plugins-Verzeichnis", wie das folgende Beispiel aus der Projektdokumentation zeigt: http://peak.telecommunity.com/DevCenter/PkgResources#locating-plugins

Beispiel für die Verwendung:

plugin_dirs = ['foo/plugins'] + sys.path
env = Environment(plugin_dirs)
distributions, errors = working_set.find_plugins(env)
map(working_set.add, distributions)  # add plugins+libs to sys.path
print("Couldn't load plugins due to: %s" % errors)

Langfristig gesehen, setuptools ist eine viel sicherere Wahl, da es Plugins ohne Konflikte oder fehlende Anforderungen laden kann.

Ein weiterer Vorteil ist, dass die Plugins selbst über denselben Mechanismus erweitert werden können, ohne dass sich die ursprünglichen Anwendungen darum kümmern müssen.

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X