package bootstrap import ( "fmt" "log" "nofx/logger" "sort" "sync" "time" ) // Priority 初始化优先级常量 const ( PriorityInfrastructure = 10 // 基础设施(日志、配置等) PriorityDatabase = 20 // 数据库连接 PriorityCore = 50 // 核心模块(Proxy、Market等) PriorityBusiness = 100 // 业务模块(Trader、API等) PriorityBackground = 200 // 后台任务 ) // ErrorPolicy 错误处理策略 type ErrorPolicy int const ( // FailFast 遇到错误立即停止(默认) FailFast ErrorPolicy = iota // ContinueOnError 继续执行,收集所有错误 ContinueOnError // WarnOnError 继续执行,只打印警告 WarnOnError ) var ( hooks []Hook hooksMu sync.Mutex ) // Register 注册初始化钩子 // name: 模块名称(如 "Proxy", "Database") // priority: 优先级(建议使用常量:PriorityCore、PriorityBusiness等) // fn: 初始化函数 func Register(name string, priority int, fn func(*Context) error) *HookBuilder { hooksMu.Lock() defer hooksMu.Unlock() hook := Hook{ Name: name, Priority: priority, Func: fn, Enabled: nil, // 默认启用 ErrorPolicy: FailFast, } hooks = append(hooks, hook) return &HookBuilder{hook: &hooks[len(hooks)-1]} } // Run 执行所有已注册的钩子 func Run(ctx *Context) error { return RunWithPolicy(ctx, FailFast) } // RunWithPolicy 使用指定的默认错误策略执行所有钩子 func RunWithPolicy(ctx *Context, defaultPolicy ErrorPolicy) error { hooksMu.Lock() hooksCopy := make([]Hook, len(hooks)) copy(hooksCopy, hooks) hooksMu.Unlock() if len(hooksCopy) == 0 { log.Printf("⚠️ 没有注册任何初始化钩子") return nil } // 按优先级排序 sort.Slice(hooksCopy, func(i, j int) bool { return hooksCopy[i].Priority < hooksCopy[j].Priority }) log.Printf("🔄 开始初始化 %d 个模块...", len(hooksCopy)) startTime := time.Now() var errors []error successCount := 0 skippedCount := 0 for i, hook := range hooksCopy { // 检查是否启用 if hook.Enabled != nil && !hook.Enabled(ctx) { log.Printf(" [%d/%d] 跳过: %s (条件未满足)", i+1, len(hooksCopy), hook.Name) skippedCount++ continue } log.Printf(" [%d/%d] 初始化: %s (优先级: %d)", i+1, len(hooksCopy), hook.Name, hook.Priority) hookStart := time.Now() err := hook.Func(ctx) elapsed := time.Since(hookStart) if err != nil { errMsg := fmt.Errorf("[%s] 初始化失败: %w", hook.Name, err) // 根据错误策略处理 policy := hook.ErrorPolicy if policy == FailFast && defaultPolicy != FailFast { policy = defaultPolicy } switch policy { case FailFast: log.Printf(" ❌ 失败: %s (耗时: %v)", hook.Name, elapsed) return errMsg case ContinueOnError: log.Printf(" ❌ 失败: %s (耗时: %v) - 继续执行", hook.Name, elapsed) errors = append(errors, errMsg) case WarnOnError: log.Printf(" ⚠️ 警告: %s (耗时: %v) - %v", hook.Name, elapsed, err) } } else { log.Printf(" ✓ 完成: %s (耗时: %v)", hook.Name, elapsed) successCount++ } } totalElapsed := time.Since(startTime) // 汇总结果 if len(errors) > 0 { logger.Log.Warnf("⚠️ 初始化完成,但有 %d 个模块失败 (总耗时: %v)", len(errors), totalElapsed) log.Printf("📊 统计: 成功=%d, 失败=%d, 跳过=%d", successCount, len(errors), skippedCount) // 返回合并的错误 return fmt.Errorf("以下模块初始化失败: %v", errors) } log.Printf("✅ 所有模块初始化完成 (总耗时: %v)", totalElapsed) log.Printf("📊 统计: 成功=%d, 跳过=%d", successCount, skippedCount) return nil } // GetRegistered 获取已注册的钩子列表(用于调试) func GetRegistered() []Hook { hooksMu.Lock() defer hooksMu.Unlock() hooksCopy := make([]Hook, len(hooks)) copy(hooksCopy, hooks) return hooksCopy } // Clear 清除所有钩子(用于测试) func Clear() { hooksMu.Lock() defer hooksMu.Unlock() hooks = nil } // Count 返回已注册的钩子数量 func Count() int { hooksMu.Lock() defer hooksMu.Unlock() return len(hooks) }