fix(plugins): restore plugin runtimes on startup + graceful shutdown
Root cause: initVault() called Discover() but never called SyncConfig(), InitRuntimes(), CallInitHooks(), or StartSchedulers(). On restart, plugins were discovered from disk but their config state (Installed/Enabled) was not restored and no Lua VMs were created. This caused: - Settings → Plugins showing plugins as 'not installed' after restart - Sidebar showing calendar item (from enabledSet config) but GetPluginPanelHTML failing (only checked p.Active) - Toggle working in-session but state lost on restart - closeVault() not stopping plugin schedulers/shutdown/VM (leak) Fixes: - bindings_config.go: add SyncConfig(appCfg) after Discover() - bindings_config.go: add InitRuntimes() + CallInitHooks() + StartSchedulers() after watcher start - bindings_config.go: add StopSchedulers + CallShutdownHooks + CloseRuntimes to closeVault() (before db.Close since plugins use DB) - bindings_plugins.go: GetPluginPanelHTML now checks enabledSet || p.Active, consistent with ListSystemViewsWithPlugins and ListPlugins
This commit is contained in:
parent
f769daa617
commit
d6e28d7b1f
|
|
@ -228,6 +228,9 @@ func (a *App) initVault(vaultPath string) error {
|
|||
}
|
||||
}
|
||||
|
||||
// Apply installed/enabled state from config to discovered plugins
|
||||
pm.SyncConfig(appCfg)
|
||||
|
||||
// Sync service
|
||||
deviceID := ""
|
||||
_ = appCfg // will store sync settings
|
||||
|
|
@ -292,6 +295,11 @@ func (a *App) initVault(vaultPath string) error {
|
|||
// Start auto-sync loop
|
||||
go a.autoSyncLoop()
|
||||
|
||||
// Start plugin runtimes for enabled plugins (creates VM, loads scripts, calls on_init)
|
||||
pm.InitRuntimes()
|
||||
pm.CallInitHooks()
|
||||
pm.StartSchedulers()
|
||||
|
||||
// Start bridge server for browser extension integration (if enabled).
|
||||
if appCfg == nil || appCfg.Vault.Bridge.Enabled {
|
||||
a.startBridge(appCfg)
|
||||
|
|
@ -313,6 +321,12 @@ func (a *App) closeVault() {
|
|||
if a.fileWatcher != nil {
|
||||
a.fileWatcher.Stop()
|
||||
}
|
||||
// Stop plugin runtimes (schedulers → on_shutdown → close VMs)
|
||||
if a.plugins != nil {
|
||||
a.plugins.StopSchedulers()
|
||||
a.plugins.CallShutdownHooks()
|
||||
a.plugins.CloseRuntimes()
|
||||
}
|
||||
// Stop bridge server.
|
||||
if a.bridge != nil {
|
||||
a.bridge.Stop()
|
||||
|
|
|
|||
|
|
@ -180,8 +180,16 @@ func (a *App) GetPluginPanelHTML(pluginName string) (string, error) {
|
|||
if a.plugins == nil {
|
||||
return "", fmt.Errorf("plugin manager not ready")
|
||||
}
|
||||
appCfg, _ := config.LoadAppConfig()
|
||||
enabledSet := make(map[string]bool)
|
||||
if appCfg != nil {
|
||||
for _, name := range appCfg.EnabledPlugins {
|
||||
enabledSet[name] = true
|
||||
}
|
||||
}
|
||||
for _, p := range a.plugins.Plugins() {
|
||||
if p.Meta.Name != pluginName || !p.Active {
|
||||
active := enabledSet[p.Meta.Name] || p.Active
|
||||
if p.Meta.Name != pluginName || !active {
|
||||
continue
|
||||
}
|
||||
if p.Meta.Panel == "" {
|
||||
|
|
|
|||
Loading…
Reference in New Issue