Vai al contenuto

Panoramica dell'architettura

Il sottosistema dei plugin è costruito su tre componenti, tutti sotto Components/:

Componente Visibilità Responsabilità
PluginApi Pubblica Interfacce puramente astratte + tipi valore. Niente Qt, niente Scintilla, nessuna intestazione interna di MTE — solo la libreria standard.
PluginHost Interna Carica, possiede e smista i plugin. Qui Qt è un dettaglio implementativo (dietro le quinte usa QPluginLoader).
Plugins Prima parte Plugin di esempio / integrati; ciascuno è un target CMake a sé che dipende solo da PluginApi (e da Qt, quando usa il backend nativo).

Principi di progettazione

  • Contratto indipendente dal backend. Tutti i tipi di PluginApi vivono nel namespace MTE::plugin e non devono includere alcuna intestazione Qt, Scintilla o interna di MTE. È questo che permette a un futuro backend Python di soddisfare lo stesso contratto senza l'attrito di Qt.
  • Nessun tipo di terze parti attraverso l'API pubblica. I plugin non vedono mai tipi Scintilla o Qt; è l'host ad adattare l'IEditorView interno al pubblico IEditorService.
  • RAII ovunque. Registrare un comando, una voce di menu, un pannello ancorabile o una sottoscrizione a eventi restituisce un token o un handle di sottoscrizione. Distruggerlo annulla la registrazione del contributo. I plugin conservano i propri token come membri, così in shutdown() viene smontato tutto automaticamente.

Ciclo di vita

Ogni plugin implementa un'unica interfaccia, IPlugin:

class IPlugin {
public:
    virtual ~IPlugin() = default;
    virtual PluginInfo info() const = 0;
    virtual bool       initialize(IPluginContext& ctx) = 0;
    virtual void       shutdown() noexcept = 0;
};
  • info() restituisce metadati POD (id, name, version, vendor, description, apiVersion).
  • initialize(ctx) riceve un localizzatore di servizi IPluginContext. Il plugin preleva i servizi che gli servono e registra i propri comandi, menu, pannelli e sottoscrizioni a eventi.
  • shutdown() viene eseguito all'uscita; poiché i contributi sono token RAII, di norma lo smontaggio si riduce a lasciar distruggere i membri.

Nessuna ricarica a caldo

Abilitare, disabilitare, installare e disinstallare un plugin hanno effetto al prossimo avvio. L'host non carica né scarica mai codice di plugin mentre è in esecuzione: questo mantiene semplice il modello ed evita il problema di Windows del «non si può eliminare una DLL caricata».

Individuazione

L'host esamina, nell'ordine:

  1. <exe-dir>/Plugins/ — i plugin di prima parte inclusi.
  2. <AppLocalData>/Plugins/ — la cartella di installazione per utente.
  3. I percorsi indicati dalla variabile d'ambiente MTE_PLUGIN_PATH.

Ogni cartella viene esaminata alla ricerca di librerie sciolte e di un livello di sottocartelle immediate (la disposizione <id>/ per plugin prodotta da un installer). L'individuazione non scende più in profondità.