{"id":"1bff3a4d6cdc0c7b","repo":"gofiber/fiber","slug":"memory-storage-s-w","errorCode":null,"errorMessage":"memory storage %s: %w","messagePattern":"memory storage (.+?): %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"warning","filePath":"internal/storage/memory/memory.go","lineNumber":243,"sourceCode":"\tkeys := make([][]byte, 0, len(s.db))\n\tfor key, v := range s.db {\n\t\t// Filter out the expired keys\n\t\tif v.expiry == 0 || v.expiry > ts {\n\t\t\tkeys = append(keys, []byte(key))\n\t\t}\n\t}\n\n\t// Double check if no valid keys were found\n\tif len(keys) == 0 {\n\t\treturn nil, nil\n\t}\n\n\treturn keys, nil\n}\n\nfunc wrapContextError(ctx context.Context, op string) error {\n\tif err := ctx.Err(); err != nil {\n\t\treturn fmt.Errorf(\"memory storage %s: %w\", op, err)\n\t}\n\treturn nil\n}\n","sourceCodeStart":225,"sourceCodeEnd":247,"githubUrl":"https://github.com/gofiber/fiber/blob/9a4c7e57fe0b080a04235d28a4b0d2b4b353d58c/internal/storage/memory/memory.go#L225-L247","documentation":"Returned by the in-memory storage adapter's *WithContext methods (GetWithContext, SetWithContext, DeleteWithContext, ResetWithContext) when the request context is already cancelled before the operation runs. wrapContextError checks ctx.Err() and wraps it with the operation name. This storage is primarily used in tests but mirrors the external storage contract.","triggerScenarios":"Calling storage.SetWithContext(ctx, ...) after ctx was already cancelled (context.Canceled) or its deadline passed (context.DeadlineExceeded). This surfaces in SaveFileToStorage flows where the request context expires before the store write, or in any code passing a request-scoped context to the memory store.","commonSituations":"Client disconnects mid-request causing the fiber context to cancel, a short request timeout firing during a slow storage op, or test code reusing an already-cancelled context.","solutions":["Use a detached context (context.Background) for storage writes that must complete even if the client disconnects.","Increase the request/server timeout if the storage op legitimately needs more time.","Check ctx.Err() before calling storage methods in latency-sensitive paths.","Handle context.Canceled / context.DeadlineExceeded explicitly and retry if appropriate."],"exampleFix":"// before\nstorage.SetWithContext(c.Context(), key, data, 0)\n\n// after\n// use a detached context so the write completes after client disconnect\nstoreCtx, cancel := context.WithTimeout(context.Background(), 5*time.Second)\ndefer cancel()\nstorage.SetWithContext(storeCtx, key, data, 0)","handlingStrategy":"validation","validationCode":"// Check context before calling a *WithContext storage method\nif ctx.Err() != nil {\n    return fmt.Errorf(\"skip storage: %w\", ctx.Err())\n}","typeGuard":null,"tryCatchPattern":"if err := storage.SetWithContext(ctx, key, data, exp); err != nil {\n    if errors.Is(err, context.Canceled) || errors.Is(err, context.DeadlineExceeded) {\n        // client gone; decide whether to finish with a detached context\n    }\n    return err\n}","preventionTips":["Use context.Background for storage writes that must complete after client disconnect.","Set adequate timeouts on request-scoped contexts.","Check ctx.Err() before expensive storage ops.","Distinguish cancellation from real storage errors in logs."],"tags":["storage","context","cancellation","go"],"analyzedSha":"9a4c7e57fe0b080a04235d28a4b0d2b4b353d58c","analyzedAt":"2026-08-04T21:44:03.395Z","schemaVersion":2}