extension

module
v0.2.3 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Feb 15, 2026 License: Apache-2.0

README

NCore Extension System

A flexible and robust extension system that provides dynamic loading, lifecycle management, dependency handling, inter-service communication, and enterprise-grade security features.

Features

  • Dynamic Loading: Load extensions from files or built-in registration
  • Dependency Management: Strong and weak dependency support with automatic resolution
  • Service Discovery: Consul-based service registration and discovery
  • Event System: Unified event handling with memory and message queue support
  • gRPC Integration: Optional gRPC service support for distributed communication
  • Circuit Breaker: Built-in fault tolerance for service calls
  • Hot Reload: Runtime plugin loading and unloading
  • Cross-Service Calls: Unified local and remote service calling interface
  • Security Sandbox: Plugin path validation, signature verification, trusted source validation
  • Resource Monitoring: Memory and CPU usage limits, performance metrics collection
  • Plugin Configuration: Personalized configuration management for each plugin

Basic Usage

Create Extension
package myext

import (
    "github.com/ncobase/ncore/extension/registry"
    "github.com/ncobase/ncore/extension/types"
)

type MyExtension struct {
    types.OptionalImpl
}

func init() {
    registry.RegisterToGroupWithWeakDeps(New(), "core", []string{"user"})
}

func (m *MyExtension) Name() string { return "my-extension" }
func (m *MyExtension) Version() string { return "1.0.0" }
func (m *MyExtension) Dependencies() []string { return []string{} }

func (m *MyExtension) Init(conf *config.Config, manager types.ManagerInterface) error {
    // Initialize extension
    return nil
}

func (m *MyExtension) GetMetadata() types.Metadata {
    return types.Metadata{
        Name: m.Name(), Version: m.Version(),
        Description: "My extension", Type: "module", Group: "core",
    }
}
Use Manager
func main() {
    mgr, err := manager.NewManager(config)
    if err != nil { panic(err) }
    defer mgr.Cleanup()

    if err := mgr.InitExtensions(); err != nil { panic(err) }
    
    ext, err := mgr.GetExtensionByName("my-extension")
    // Use extension...
}

Extension Lifecycle

Extensions follow a structured initialization process:

  1. Registration - Auto-registered via init() or manually with manager.RegisterExtension()
  2. Dependency Resolution - System calculates initialization order based on dependencies
  3. Pre-initialization - PreInit() method for early setup
  4. Initialization - Init(config, manager) method with full context
  5. Post-initialization - PostInit() method for cross-extension communication
  6. Runtime - Extension is active and serving requests
  7. Cleanup - PreCleanup() and Cleanup() methods for resource cleanup

Dependency Management

Dependency Types

Strong Dependencies - Required and must be initialized first:

func (m *MyExtension) Dependencies() []string {
    return []string{"required-module"}
}

Weak Dependencies - Optional, graceful degradation when missing:

func (m *MyExtension) GetAllDependencies() []types.DependencyEntry {
    return []types.DependencyEntry{
        {Name: "required-module", Type: types.StrongDependency},
        {Name: "optional-module", Type: types.WeakDependency},
    }
}
Dependency Resolution

The system automatically:

  • Detects and prevents circular dependencies
  • Calculates optimal initialization order
  • Handles missing weak dependencies gracefully
  • Provides detailed error messages for resolution failures

Extensions with weak dependencies should handle missing services:

func (m *MyExtension) PostInit() error {
    if userService, err := m.manager.GetServiceByName("user"); err == nil {
        m.userService = userService
    } else {
        log.Warn("User service unavailable, limited functionality")
    }
    return nil
}

Service Communication

Service Calling Strategies
// Default local-first strategy
result, err := manager.CallService(ctx, "user-service", "GetUser", userID)

// Explicit strategy
result, err := manager.CallServiceWithOptions(ctx, "user-service", "GetUser", userID, 
    &types.CallOptions{
        Strategy: types.LocalFirst,  // LocalFirst, RemoteFirst, LocalOnly, RemoteOnly
        Timeout:  30 * time.Second,
    })

Strategy Behavior:

  • LocalFirst: Try local service, fallback to gRPC
  • RemoteFirst: Try gRPC service, fallback to local
  • LocalOnly: Local service only, fail if unavailable
  • RemoteOnly: gRPC service only, fail if unavailable
Cross-Service Access
// Direct service access
userService, err := manager.GetServiceByName("user")

// Cross-service field access
authService, err := manager.GetCrossService("auth", "TokenManager")

Event System

Event Targets

The event system supports multiple transport mechanisms:

  • EventTargetMemory: In-memory, single instance, high performance
  • EventTargetQueue: Message queue (RabbitMQ/Kafka), distributed, persistent
  • EventTargetAll: Both targets simultaneously
Event Operations
// Subscribe (auto-selects best transport)
manager.SubscribeEvent("user.created", func(data any) {
    eventData := data.(types.EventData)
    // Handle event
})

// Subscribe to specific transport
manager.SubscribeEvent("user.created", handler, types.EventTargetMemory)

// Publish (auto-selects best transport)
manager.PublishEvent("user.created", userData)

// Publish with retry for critical events
manager.PublishEventWithRetry("payment.failed", paymentData, 3)
Event Data Structure
type EventData struct {
    Time      time.Time `json:"time"`
    Source    string    `json:"source"`
    EventType string    `json:"event_type"`
    Data      any       `json:"data"`
}

Security & Performance Features

Security Sandbox

The system provides comprehensive security controls:

// Plugin configuration management
config := map[string]any{
    "cache_ttl": "1h",
    "max_connections": 100,
}
manager.SetPluginConfig("my-plugin", config)

// Get plugin configuration
if cfg, exists := manager.GetPluginConfig("my-plugin"); exists {
    // Use configuration
}
Resource Monitoring
// Get resource usage metrics
metrics := manager.GetResourceMetrics()
for pluginName, metric := range metrics {
    fmt.Printf("Plugin %s: memory=%fMB, cpu=%f%%, load_time=%v\n", 
        pluginName, metric.MemoryUsageMB, metric.CPUUsagePercent, metric.LoadTime)
}

// Get security status
securityStatus := manager.GetSecurityStatus()
fmt.Printf("Security status: %+v\n", securityStatus)
Enhanced Metrics
// Get comprehensive metrics including security, performance, and system info
enhancedMetrics := manager.GetEnhancedMetrics()

Configuration

extension:
  path: "./plugins"          # Plugin directory
  mode: "file"              # "file" or "c2hlbgo" (built-in)
  includes: ["auth", "user"] # Include specific plugins
  excludes: ["debug"]       # Exclude plugins
  hot_reload: true          # Hot reload support
  
  # Advanced configuration
  max_plugins: 50           # Maximum number of plugins
  
  # Security configuration
  security:
    enable_sandbox: true    # Enable security sandbox
    allowed_paths:          # Allowed plugin paths
      - "/opt/plugins"
      - "/usr/local/plugins"
    blocked_extensions:     # Blocked file extensions
      - ".exe"
      - ".bat"
    trusted_sources:        # Trusted plugin sources
      - "company.com"
      - "verified.org"
    require_signature: true # Require plugin signature
  
  # Performance configuration
  performance:
    max_memory_mb: 512      # Maximum memory usage (MB)
    max_cpu_percent: 80     # Maximum CPU usage (%)
    enable_metrics: true    # Enable performance metrics
    metrics_interval: "30s" # Metrics collection interval
    enable_profiling: false # Enable performance profiling
    gc_interval: "5m"       # Garbage collection interval
  
  # Plugin-specific configuration
  plugin_config:
    auth_plugin:
      oauth_providers: ["google", "github"]
    user_plugin:
      cache_ttl: "1h"

consul:
  address: "localhost:8500"  # Consul server
  scheme: "http"
  discovery:
    health_check: true       # Enable health checks
    check_interval: "10s"    # Health check interval
    timeout: "3s"           # Health check timeout

grpc:
  enabled: true             # Enable gRPC support
  host: "localhost"
  port: 9090

Advanced Features

gRPC Integration

Extensions can provide gRPC services:

func (m *MyExtension) RegisterGRPCServices(server *grpc.Server) {
    pb.RegisterMyServiceServer(server, m.grpcService)
}
Service Discovery

Extensions can register with service discovery:

func (m *MyExtension) NeedServiceDiscovery() bool { return true }

func (m *MyExtension) GetServiceInfo() *types.ServiceInfo {
    return &types.ServiceInfo{
        Address: "localhost:8080",
        Tags:    []string{"api", "v1"},
        Meta:    map[string]string{"version": "1.0"},
    }
}
Circuit Breaker

Protect against service failures:

result, err := manager.ExecuteWithCircuitBreaker("external-service", func() (any, error) {
    return callExternalAPI()
})
Plugin Loading Modes

File Mode: Load plugins from filesystem

  • Supports .so files on Linux, .dll on Windows
  • Hot reload capability
  • Include/exclude filtering
  • Security sandbox protection

Built-in Mode: Use statically compiled extensions

  • Better performance and security
  • No filesystem dependencies
  • Compile-time dependency resolution

Management API

REST endpoints for runtime management:

  • GET /exts - List all extensions with metadata
  • GET /exts/status - Get extension status and health
  • POST /exts/load?name=plugin - Load specific plugin
  • POST /exts/unload?name=plugin - Unload plugin
  • POST /exts/reload?name=plugin - Reload plugin
  • GET /exts/metrics - System metrics and performance data
  • GET /exts/metrics/security - Security status metrics
  • GET /exts/metrics/performance - Performance monitoring metrics

Performance Considerations

  • Service Discovery: Use appropriate cache TTL (default 30s)
  • Event Transport: Choose memory for high-frequency, queue for reliability
  • Circuit Breaker: Monitor failure rates and adjust thresholds
  • Plugin Loading: Prefer built-in mode for production environments
  • Resource Monitoring: Enable performance metrics collection as needed
  • Security Checks: Balance security requirements with performance needs

Troubleshooting

Common Issues

Circular Dependencies

Error: cyclic dependency detected in extensions: [module-a, module-b]

Solution: Convert one dependency to weak dependency type

Service Not Found

Error: extension 'user-service' not found

Solution: Check extension registration and initialization order

gRPC Connection Failed

Error: failed to get gRPC connection for service-name  

Solution: Verify service discovery configuration and network connectivity

Security Validation Failed

Error: security validation failed: path /tmp/plugin.so is not in allowed paths

Solution: Check allowed paths configuration in security settings

Resource Limit Exceeded

Error: resource limit check failed: insufficient memory: would exceed limit of 512MB

Solution: Adjust resource limits in performance configuration or optimize plugin memory usage

Plugin Signature Validation Failed

Error: signature validation failed: plugin signature not found

Solution: Ensure plugin file has corresponding .sig signature file or disable signature verification

Directories

Path Synopsis
Package grpc provides gRPC server and client infrastructure with automatic service discovery, health checks, and connection pooling.
Package grpc provides gRPC server and client infrastructure with automatic service discovery, health checks, and connection pooling.
Package metrics provides comprehensive metrics collection, aggregation, and monitoring for extensions and application components.
Package metrics provides comprehensive metrics collection, aggregation, and monitoring for extensions and application components.
Package security provides security controls and sandboxing for extension loading and execution, including plugin signature verification and resource monitoring.
Package security provides security controls and sandboxing for extension loading and execution, including plugin signature verification and resource monitoring.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL