{"record":{"id":"b4a2b0488eb1d243","repo":"Tencent/WeKnora","slug":"delete-remote-sandbox-w","errorCode":null,"errorMessage":"delete remote sandbox: %w","messagePattern":"delete remote sandbox: %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/sandbox/session_lifecycle.go","lineNumber":487,"sourceCode":"\t\t\treturn fmt.Errorf(\n\t\t\t\t\"delete duplicate owned remote sandbox %q: %w\",\n\t\t\t\tcandidate.ID,\n\t\t\t\terr,\n\t\t\t)\n\t\t}\n\t}\n\treturn nil\n}\n\nfunc (l *remoteSessionLifecycle) destroyBindingLocked(\n\tctx context.Context,\n\tkey SessionSandboxKey,\n\tbinding SessionSandboxBinding,\n) error {\n\tif binding.Provider == l.client.Provider() {\n\t\terr := l.client.Delete(ctx, binding.SandboxID)\n\t\tif err != nil && !CanReplaceRemoteBinding(err) {\n\t\t\treturn fmt.Errorf(\"delete remote sandbox: %w\", err)\n\t\t}\n\t}\n\n\tdeleted, err := l.bindings.DeleteIfMatch(\n\t\tctx,\n\t\tkey,\n\t\tbinding.Provider,\n\t\tbinding.SandboxID,\n\t)\n\tif err != nil {\n\t\treturn fmt.Errorf(\"delete sandbox binding: %w\", err)\n\t}\n\tif deleted {\n\t\treturn nil\n\t}\n\tcurrent, err := l.readBinding(ctx, key)\n\tif err != nil {\n\t\treturn err","sourceCodeStart":469,"sourceCodeEnd":505,"githubUrl":"https://github.com/Tencent/WeKnora/blob/988cbb03305e055d8ebb7d46d9ac6cc0803cd074/internal/sandbox/session_lifecycle.go#L469-L505","documentation":"destroyBindingLocked deletes the remote sandbox backing a session binding before removing the binding record. If the provider Delete call fails and the error is not recognized as a benign 'binding replaceable' condition (CanReplaceRemoteBinding), the destroy is aborted with this wrapped error, leaving the sandbox running and the binding intact.","triggerScenarios":"Session destroy / resolve path calls client.Delete(binding.SandboxID) and the provider returns a persistent error: network failure, 4xx/5xx, wrong credentials, or the sandbox in a state where deletion is rejected and not deemed replaceable.","commonSituations":"Provider outage during teardown; deleted/expired sandbox IDs (binding points at a stale sandbox); IAM/credentials lacking delete permission on the provider account.","solutions":["Read the wrapped provider error; if the sandbox no longer exists, the binding may point to a stale record — reconcile the store","Retry the destroy operation after transient provider failures","Verify provider credentials/permissions allow deleting sandboxes","Check CanReplaceRemoteBinding semantics: errors considered 'replaceable' are intentionally swallowed; anything else is fatal here"],"exampleFix":null,"handlingStrategy":"try-catch","validationCode":null,"typeGuard":null,"tryCatchPattern":"err := manager.DestroySession(ctx, key)\nif err != nil && strings.Contains(err.Error(), \"delete remote sandbox\") {\n    // inspect wrapped provider error; decide retry vs manual reconcile\n    log.Printf(\"destroy failed: %v\", err)\n}","preventionTips":["Ensure provider credentials grant delete permission","Treat repeated destroy failures as alerts — they leak billable sandboxes","Reconcile binding store vs provider inventory on a schedule"],"tags":["go","remote-provider","delete","teardown","stale-binding"],"backgroundTag":"remote-resource-delete-failed","analyzedSha":"988cbb03305e055d8ebb7d46d9ac6cc0803cd074","analyzedAt":"2026-09-02T14:41:08.344Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-08T10:18:20.063Z"}