oncetask provides hard delete functionality to permanently remove tasks from Firestore. Unlike cancellation which marks tasks as cancelled but keeps them in the database, deletion permanently removes task documents.
err := manager.DeleteTask(ctx, taskID)Permanently removes a specific task by its ID.
count, err := manager.DeleteTasksByIds(ctx, []string{"id1", "id2", "id3"})Permanently removes multiple tasks by their IDs in a single operation. Returns the number of tasks deleted.
When a task is deleted:
- Document is removed from Firestore - The task is permanently deleted with no way to recover it
- No cleanup handlers run - Unlike cancellation, deletion does not trigger any handlers
- No audit trail - The task is gone with no record of its existence
| Aspect | Deletion | Cancellation |
|---|---|---|
| Data retention | Permanently removed | Kept with isCancelled=true |
| Cleanup handlers | Not triggered | Triggered if registered |
| Audit trail | None | cancelledAt timestamp preserved |
| Recoverable | No | Task data still available |
| Use case | Cleanup old/test data | Graceful task termination |
When to use deletion:
- Cleaning up old completed/failed tasks
- Removing test data
- Purging tasks after data retention period
- Removing erroneously created tasks
When to use cancellation:
- Stopping a task that's no longer needed
- Graceful shutdown with cleanup
- When you need audit trail of what was cancelled
Deletion operations are idempotent:
- Deleting a non-existent task returns no error
- Re-deleting an already deleted task succeeds
// Both calls succeed, second one is a no-op
manager.DeleteTask(ctx, "task-123")
manager.DeleteTask(ctx, "task-123") // No errorDeletion respects environment boundaries set by ONCE_TASK_ENV:
// Only deletes tasks in current environment
os.Setenv("ONCE_TASK_ENV", "production")
manager.DeleteTask(ctx, taskID) // Deletes if task.Env == "production"Important: Attempting to delete a task from a different environment will return an error:
os.Setenv("ONCE_TASK_ENV", "production")
// If task belongs to "staging" environment
err := manager.DeleteTask(ctx, taskID) // Returns error: "task XYZ is in different environment"You can delete tasks that are currently being executed (leased):
// This works, but has consequences
manager.DeleteTask(ctx, leasedTaskID)Warning: If you delete a leased task:
- The handler continues running until completion
- When the handler tries to update the task status, it will fail (document not found)
- The handler's side effects (external API calls, etc.) still occur
Recommendation: Cancel tasks instead of deleting them if they might be running.
Bulk deletion can have partial failures:
count, err := manager.DeleteTasksByIds(ctx, []string{"id1", "id2", "id3"})
if err != nil {
// Some deletions may have succeeded
log.Printf("Deleted %d tasks, but encountered errors: %v", count, err)
}The returned count indicates how many tasks were successfully deleted, even if some failed.
// Get tasks by resource key, filter completed ones, delete
tasks, err := manager.GetTasksByResourceKey(ctx, "user-123")
if err != nil {
return err
}
var oldTaskIDs []string
for _, task := range tasks {
if task.GetStatus() == oncetask.TaskStatusCompleted {
oldTaskIDs = append(oldTaskIDs, task.Id)
}
}
count, err := manager.DeleteTasksByIds(ctx, oldTaskIDs)
log.Printf("Deleted %d old tasks", count)// After integration tests, clean up test tasks
testTaskIDs := []string{
"test-task-1",
"test-task-2",
"test-task-3",
}
count, err := manager.DeleteTasksByIds(ctx, testTaskIDs)
if err != nil {
log.Printf("Warning: test cleanup had errors: %v", err)
}// Oops, created a task with wrong data
err := manager.DeleteTask(ctx, "wrong-task-id")
if err != nil {
log.Printf("Failed to delete task: %v", err)
}If a task might be running or needs cleanup:
// Better: cancel first, then delete later if needed
manager.CancelTask(ctx, taskID)
// Later, after task is done-cancelled:
manager.DeleteTask(ctx, taskID)Use DeleteTasksByIds for multiple tasks:
// Efficient: single bulk operation
manager.DeleteTasksByIds(ctx, taskIDs)
// Inefficient: multiple round trips
for _, id := range taskIDs {
manager.DeleteTask(ctx, id)
}Always check both count and error:
count, err := manager.DeleteTasksByIds(ctx, taskIDs)
if err != nil {
log.Printf("Partial deletion: %d/%d succeeded, error: %v",
count, len(taskIDs), err)
}Before deleting, ensure you don't need the task data for:
- Audit logs
- Debugging
- Analytics
- Compliance requirements
- Learn about Cancellation for graceful task termination
- Explore Configuration for retry policies
- Understand Task Types for different execution patterns