-
Notifications
You must be signed in to change notification settings - Fork 1
Feature: Add recover pending for redis stream_queue #14
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -50,6 +50,7 @@ func NewService( | |
| } | ||
| } | ||
|
|
||
| // StartPaperIngest creates and enqueues a paper ingestion task. | ||
| func (s *Service) StartPaperIngest(ctx context.Context, paperID string) (task.Task, error) { | ||
| paperID = strings.TrimSpace(paperID) | ||
| if paperID == "" { | ||
|
|
@@ -105,6 +106,7 @@ func (s *Service) StartPaperIngest(ctx context.Context, paperID string) (task.Ta | |
| return job, nil | ||
| } | ||
|
|
||
| // StartPaperReindex creates and enqueues a paper reindex task. | ||
| func (s *Service) StartPaperReindex(ctx context.Context, paperID string) (task.Task, error) { | ||
| paperID = strings.TrimSpace(paperID) | ||
| if paperID == "" { | ||
|
|
@@ -153,6 +155,7 @@ func (s *Service) StartPaperReindex(ctx context.Context, paperID string) (task.T | |
| return job, nil | ||
| } | ||
|
|
||
| // runPDFTextIngest parses a PDF and stores its generated artifacts and chunks. | ||
| func (s *Service) runPDFTextIngest(ctx context.Context, job task.Task, paper domain.Paper) error { | ||
| // precheck | ||
| if s.parser == nil { | ||
|
|
@@ -236,7 +239,7 @@ func (s *Service) runPDFTextIngest(ctx context.Context, job task.Task, paper dom | |
| return nil | ||
| } | ||
|
|
||
| // fail set failed status for paper and task | ||
| // fail marks both the paper and task as failed. | ||
| func (s *Service) fail(ctx context.Context, job task.Task, paper domain.Paper, err error) { | ||
| opCtx, cancel := context.WithTimeout(context.Background(), 15*time.Second) | ||
| defer cancel() | ||
|
|
@@ -254,6 +257,7 @@ func (s *Service) fail(ctx context.Context, job task.Task, paper domain.Paper, e | |
| _ = s.tasks.Update(opCtx, job) | ||
| } | ||
|
|
||
| // failTaskOnly marks only the task as failed. | ||
| func (s *Service) failTaskOnly(ctx context.Context, job task.Task, err error) { | ||
| opCtx, cancel := context.WithTimeout(context.Background(), 15*time.Second) | ||
| defer cancel() | ||
|
|
@@ -266,7 +270,7 @@ func (s *Service) failTaskOnly(ctx context.Context, job task.Task, err error) { | |
| _ = s.tasks.Update(opCtx, job) | ||
| } | ||
|
|
||
| // downloadOriginalPDF download original PDF to tmp | ||
| // downloadOriginalPDF downloads the original PDF to a temporary local file. | ||
| func (s *Service) downloadOriginalPDF(ctx context.Context, paper domain.Paper) (string, func(), error) { | ||
| if s.store == nil { | ||
| return "", nil, fmt.Errorf("object storage is not initialized") | ||
|
|
@@ -323,6 +327,7 @@ func parsedMarkdown(paper domain.Paper, doc docparser.Document) string { | |
| return b.String() | ||
| } | ||
|
|
||
| // ReindexPaper rebuilds a paper's Elasticsearch index from MySQL chunks. | ||
| func (s *Service) ReindexPaper(ctx context.Context, paperID string) error { | ||
| if s.search == nil { | ||
| return fmt.Errorf("search backend is not initialized") | ||
|
|
@@ -355,6 +360,7 @@ func (s *Service) ReindexPaper(ctx context.Context, paperID string) error { | |
| return nil | ||
| } | ||
|
|
||
| // ProcessPaperIngest executes a queued paper ingestion task. | ||
| func (s *Service) ProcessPaperIngest(ctx context.Context, paperID, taskID string) error { | ||
| taskID = strings.TrimSpace(taskID) | ||
| paperID = strings.TrimSpace(paperID) | ||
|
|
@@ -370,6 +376,9 @@ func (s *Service) ProcessPaperIngest(ctx context.Context, paperID, taskID string | |
| if !ok { | ||
| return fmt.Errorf("task %s not found", taskID) | ||
| } | ||
| if job.Status == task.Succeeded { | ||
| return nil | ||
| } | ||
|
Comment on lines
+379
to
+381
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🗄️ Data Integrity & Integration | 🟠 Major | ⚡ Quick win Fix the ingest caller’s argument order before relying on this guard.
Proposed fix- return h.ingest.ProcessPaperIngest(ctx, taskID, paperID)
+ return h.ingest.ProcessPaperIngest(ctx, paperID, taskID)🤖 Prompt for AI Agents |
||
|
|
||
| paper, err := s.papers.Get(ctx, paperID) | ||
| if err != nil { | ||
|
|
@@ -383,6 +392,7 @@ func (s *Service) ProcessPaperIngest(ctx context.Context, paperID, taskID string | |
| return nil | ||
| } | ||
|
|
||
| // ProcessPaperReindex executes a queued paper reindex task. | ||
| func (s *Service) ProcessPaperReindex(ctx context.Context, paperID, taskID string) error { | ||
| taskID = strings.TrimSpace(taskID) | ||
| paperID = strings.TrimSpace(paperID) | ||
|
|
@@ -398,6 +408,9 @@ func (s *Service) ProcessPaperReindex(ctx context.Context, paperID, taskID strin | |
| if !ok { | ||
| return fmt.Errorf("task %s not found", taskID) | ||
| } | ||
| if job.Status == task.Succeeded { | ||
| return nil | ||
| } | ||
|
|
||
| now := time.Now() | ||
| job.Status = task.Running | ||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🩺 Stability & Availability | 🟠 Major | ⚡ Quick win
First pending-recovery pass is delayed by a full
claimIntervalafter startup.lastClaimAt := time.Now()is set immediately before the loop, sotime.Since(lastClaimAt) >= w.claimIntervalis false on the first iteration andrecoverPendingis skipped until an interval has elapsed. Since a core goal of this feature is recovering jobs left pending by a previously-crashed worker, delaying that first recovery attempt (default 1 minute, configurable) seems counter to intent.♻️ Proposed fix
📝 Committable suggestion
🤖 Prompt for AI Agents