feat: support durable task cancellation without foreign keys
This commit is contained in:
35
internal/storage/mysql/worker_cancellation.go
Normal file
35
internal/storage/mysql/worker_cancellation.go
Normal file
@@ -0,0 +1,35 @@
|
||||
package mysql
|
||||
|
||||
import (
|
||||
"context"
|
||||
"database/sql"
|
||||
|
||||
"git.yuntuo.hk/k2safe/orbit/platform/auth"
|
||||
"git.yuntuo.hk/k2safe/orbit/pulse/worker"
|
||||
)
|
||||
|
||||
// Cancellations 读取当前有效会话持有的取消意图;断线后由新会话 Resume 和扫描重新交付。
|
||||
// 通知允许重复或迟到,不能代替任务结果;256 对应单 Worker 最大持久化容量。
|
||||
func (s *ExecutionStore) Cancellations(ctx context.Context, token auth.Token, b worker.Binding) ([]worker.Cancellation, error) {
|
||||
out := []worker.Cancellation{}
|
||||
err := s.transaction(ctx, token, "workers:consume", func(tx *sql.Tx, p auth.Permissions) error {
|
||||
state, err := s.lockSession(ctx, tx, token, b, p)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
rows, err := tx.QueryContext(ctx, `SELECT t.id,a.id,a.epoch,t.cancel_requested_at FROM pulse_attempts a JOIN pulse_tasks t ON t.namespace_id=a.namespace_id AND t.id=a.task_id AND t.current_attempt_id=a.id WHERE a.namespace_id=? AND a.session_id=? AND a.state='RUNNING' AND t.state='RUNNING' AND t.queue_id=? AND t.cancel_requested_at IS NOT NULL ORDER BY a.id LIMIT 256`, token.NamespaceID, b.SessionID, state.queue)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
defer rows.Close()
|
||||
for rows.Next() {
|
||||
var c worker.Cancellation
|
||||
if err := rows.Scan(&c.TaskID, &c.AttemptID, &c.Epoch, &c.RequestedAt); err != nil {
|
||||
return err
|
||||
}
|
||||
out = append(out, c)
|
||||
}
|
||||
return rows.Err()
|
||||
})
|
||||
return out, err
|
||||
}
|
||||
Reference in New Issue
Block a user