package job import ( "context" "log" "time" jobdom "haixun-backend/internal/model/job/domain/usecase" threadsaccountdomain "haixun-backend/internal/model/threads_account/domain/usecase" ) const refreshThreadsTokenTemplateType = "refresh-threads-token" type ThreadsTokenSweeper struct { accounts threadsaccountdomain.UseCase jobs jobdom.UseCase leadTime time.Duration } func NewThreadsTokenSweeper( accounts threadsaccountdomain.UseCase, jobs jobdom.UseCase, leadTime time.Duration, ) *ThreadsTokenSweeper { if leadTime <= 0 { leadTime = 7 * 24 * time.Hour } return &ThreadsTokenSweeper{ accounts: accounts, jobs: jobs, leadTime: leadTime, } } func (s *ThreadsTokenSweeper) Start(ctx context.Context, interval time.Duration) { if s == nil || s.accounts == nil || s.jobs == nil { return } if interval <= 0 { interval = time.Hour } log.Printf("threads token sweeper started: interval=%s lead_time=%s", interval, s.leadTime) ticker := time.NewTicker(interval) defer ticker.Stop() for { select { case <-ctx.Done(): log.Printf("threads token sweeper stopped") return case <-ticker.C: created, err := s.tick(ctx) if err != nil { log.Printf("threads token sweeper tick error: %v", err) continue } if created > 0 { log.Printf("threads token sweeper enqueued %d refresh job(s)", created) } } } } func (s *ThreadsTokenSweeper) tick(ctx context.Context) (int, error) { candidates, err := s.accounts.ListTokenRefreshCandidates(ctx, s.leadTime) if err != nil { return 0, err } created := 0 for _, item := range candidates { if item.AccountID == "" || item.TenantID == "" || item.OwnerUID == "" { continue } _, err := s.jobs.CreateRun(ctx, jobdom.CreateRunRequest{ TemplateType: refreshThreadsTokenTemplateType, Scope: "threads_account", ScopeID: item.AccountID, TenantID: item.TenantID, OwnerUID: item.OwnerUID, Payload: map[string]any{ "tenant_id": item.TenantID, "owner_uid": item.OwnerUID, "account_id": item.AccountID, "expires_at": item.ExpiresAt, }, }) if err != nil { log.Printf("threads token sweeper skip account=%s: %v", item.AccountID, err) continue } created++ } return created, nil }