Skip to main content
Version: 0.4.x(Latest)

Introduction​

Lifecycle declarations cover callback registration for plugin governance operations such as install, upgrade, disable, and uninstall. Source plugins register Go callback functions through pluginhost.Declarations.Lifecycle(), while dynamic plugins declare lifecycle callback contracts through LifecycleContract.

Capability Phase: Declaration

Supported Plugin Types: Source plugins, dynamic plugins

Capability Design​

Lifecycle Hook Categories​

Lifecycle hooks are divided into two types: before hooks (Before) and after hooks (After). Before hooks can veto an operation, while after hooks are used for observation and cleanup.

Lifecycle Hook List​

HookTypeVetoableDescription
BeforeInstallBeforeYesPre-installation validation; returning ok=false prevents installation
AfterInstallAfterNoPost-installation initialization for creating default data or configuration
BeforeUpgradeBeforeYesPre-upgrade validation; returning ok=false prevents upgrade
UpgradeCustomNoExecutes custom upgrade logic
AfterUpgradeAfterNoPost-upgrade cleanup or observation
BeforeDisableBeforeYesPre-disable validation; returning ok=false prevents disabling
AfterDisableAfterNoPost-disable cleanup
BeforeUninstallBeforeYesPre-uninstallation validation; returning ok=false prevents uninstallation
UninstallCustomNoExecutes uninstall cleanup logic, such as clearing plugin data
AfterUninstallAfterNoPost-uninstallation observation
BeforeTenantDisableBeforeYesPre-tenant-disable validation
AfterTenantDisableAfterNoPost-tenant-disable cleanup
BeforeTenantDeleteBeforeYesPre-tenant-delete validation
AfterTenantDeleteAfterNoPost-tenant-delete cleanup
BeforeInstallModeChangeBeforeYesPre-install-mode-change validation
AfterInstallModeChangeAfterNoPost-install-mode-change cleanup

Callback Timeouts​

ParameterDefaultDescription
Single callback timeout5 secondsMaximum execution time for a single lifecycle callback
Aggregate timeout10 secondsTotal execution time for all plugin callbacks under the same hook

Input Parameters​

Input InterfaceApplicable HooksKey Fields
SourcePluginLifecycleInputInstall, disable, uninstallPluginID(), Operation(), StartupAutoEnable(), PurgeStorageData()
SourcePluginUpgradeInputUpgradePluginID(), FromVersion(), ToVersion(), FromManifest(), ToManifest()
SourcePluginTenantLifecycleInputTenant disable, tenant deleteOperation(), TenantID()
SourcePluginInstallModeChangeInputInstall mode changePluginID(), Operation(), FromMode(), ToMode()
SourcePluginUninstallInputUninstall cleanupPluginID(), PurgeStorageData(), Services()

Interface Definition​

Source Plugin Interface​

Source plugins register lifecycle callbacks through Lifecycle():

MethodCallback TypeDescription
RegisterBeforeInstallHandlerSourcePluginBeforeLifecycleHandlerPre-installation validation
RegisterAfterInstallHandlerSourcePluginAfterLifecycleHandlerPost-installation initialization
RegisterBeforeUpgradeHandlerSourcePluginBeforeUpgradeHandlerPre-upgrade validation
RegisterUpgradeHandlerSourcePluginUpgradeHandlerCustom upgrade logic
RegisterAfterUpgradeHandlerSourcePluginUpgradeHandlerPost-upgrade cleanup
RegisterBeforeDisableHandlerSourcePluginBeforeLifecycleHandlerPre-disable validation
RegisterAfterDisableHandlerSourcePluginAfterLifecycleHandlerPost-disable cleanup
RegisterBeforeUninstallHandlerSourcePluginBeforeLifecycleHandlerPre-uninstallation validation
RegisterAfterUninstallHandlerSourcePluginAfterLifecycleHandlerPost-uninstallation cleanup
RegisterBeforeTenantDisableHandlerSourcePluginBeforeTenantLifecycleHandlerPre-tenant-disable validation
RegisterAfterTenantDisableHandlerSourcePluginAfterTenantLifecycleHandlerPost-tenant-disable cleanup
RegisterBeforeTenantDeleteHandlerSourcePluginBeforeTenantLifecycleHandlerPre-tenant-delete validation
RegisterAfterTenantDeleteHandlerSourcePluginAfterTenantLifecycleHandlerPost-tenant-delete cleanup
RegisterBeforeInstallModeChangeHandlerSourcePluginBeforeInstallModeChangeHandlerPre-install-mode-change validation
RegisterAfterInstallModeChangeHandlerSourcePluginAfterInstallModeChangeHandlerPost-install-mode-change cleanup
RegisterUninstallHandlerSourcePluginUninstallHandlerUninstall cleanup logic

Dynamic Plugin Interface​

Dynamic plugins declare lifecycle callback contracts through LifecycleContract. Each contract defines an operation and its corresponding WASM entry point:

FieldTypeDescription
operationstringLifecycle operation name
requestTypestringRequest DTO name
internalPathstringInternal route path
timeoutMsintCallback timeout in milliseconds

Supported operation values: BeforeInstall, AfterInstall, BeforeUpgrade, Upgrade, AfterUpgrade, BeforeDisable, AfterDisable, BeforeUninstall, Uninstall, AfterUninstall, BeforeTenantDisable, AfterTenantDisable, BeforeTenantDelete, AfterTenantDelete, BeforeInstallModeChange, AfterInstallModeChange.

Usage​

Source Plugin Usage​

Source plugins register lifecycle callbacks in init() through the grouped Lifecycle() entry:

func init() {
plugin := pluginhost.NewDeclarations("my-author-my-domain-my-cap")

if err := plugin.Lifecycle().RegisterBeforeInstallHandler(beforeInstall); err != nil {
panic(err)
}
if err := plugin.Lifecycle().RegisterAfterInstallHandler(afterInstall); err != nil {
panic(err)
}

if err := pluginhost.RegisterSourcePlugin(plugin); err != nil {
panic(err)
}
}

Before hooks can veto an operation by returning ok=false and a reason:

func beforeInstall(ctx context.Context, input pluginhost.SourcePluginLifecycleInput) (ok bool, reason string, err error) {
// Validate dependencies
if !checkDependencies() {
return false, "Missing required dependencies", nil
}
return true, "", nil
}

After hooks are used for initialization or cleanup:

func afterInstall(ctx context.Context, input pluginhost.SourcePluginLifecycleInput) error {
// Create default configuration
return createDefaultConfig(ctx)
}

Dynamic Plugin Usage​

Dynamic plugins embed LifecycleContract in the .wasm artifact. The build tool automatically extracts lifecycle contracts from controllers in the backend/ directory:

// backend/lifecycle.go
//go:build wasm

package backend

// Controller methods correspond to lifecycle operations
func (c *LifecycleController) BeforeInstall(ctx context.Context, req *BeforeInstallReq) (*LifecycleDecision, error) {
// Pre-installation validation
return &LifecycleDecision{OK: true}, nil
}

func (c *LifecycleController) AfterInstall(ctx context.Context, req *AfterInstallReq) (*LifecycleDecision, error) {
// Post-installation initialization
return &LifecycleDecision{OK: true}, nil
}

The build tool automatically generates LifecycleContract and embeds it in the lina.plugin.backend.lifecycle custom section of the .wasm artifact.

Design Constraints​

  • Before hooks can veto operations. When ok=false is returned, the host prevents subsequent operations from executing.
  • After hooks cannot veto operations. After hooks execute after the operation completes; failures are only logged and do not roll back the operation.
  • Uninstall cleanup is a separate hook. The Uninstall hook handles data cleanup and is separate from BeforeUninstall and AfterUninstall.
  • Timeout mechanism protects the host. Single callback timeout is 5 seconds, aggregate timeout is 10 seconds; callbacks are terminated on timeout.
  • Dynamic plugin lifecycle goes through bridge contracts. Dynamic plugin lifecycle callbacks execute through the WASM bridge and are not exposed through hostServices.
  • PurgeStorageData controls data cleanup. During uninstallation, the host uses this flag to notify the plugin whether persistent data needs to be cleared.