{"record":{"id":"4c1ddca8fd1230cd","repo":"bumptech/glide","slug":"you-cannot-modify-locked-t-consider-clone","errorCode":null,"errorMessage":"You cannot modify locked T, consider clone()","messagePattern":"You cannot modify locked T, consider clone\\(\\)","errorType":"exception","errorClass":"IllegalStateException","httpStatus":null,"severity":"error","filePath":"library/src/main/java/com/bumptech/glide/request/BaseRequestOptions.java","lineNumber":1314,"sourceCode":"   *\n   * <p>Auto clone is not retained by cloned objects returned from mutations. The cloned objects are\n   * mutable and are not locked.\n   */\n  @NonNull\n  public T autoClone() {\n    if (isLocked && !isAutoCloneEnabled) {\n      throw new IllegalStateException(\n          \"You cannot auto lock an already locked options object\" + \", try clone() first\");\n    }\n    isAutoCloneEnabled = true;\n    return lock();\n  }\n\n  @NonNull\n  @SuppressWarnings(\"unchecked\")\n  protected final T selfOrThrowIfLocked() {\n    if (isLocked) {\n      throw new IllegalStateException(\"You cannot modify locked T, consider clone()\");\n    }\n    return self();\n  }\n\n  protected final boolean isAutoCloneEnabled() {\n    return isAutoCloneEnabled;\n  }\n\n  public final boolean isDiskCacheStrategySet() {\n    return isSet(DISK_CACHE_STRATEGY);\n  }\n\n  public final boolean isSkipMemoryCacheSet() {\n    return isSet(IS_CACHEABLE);\n  }\n\n  @NonNull\n  public final Map<Class<?>, Transformation<?>> getTransformations() {","sourceCodeStart":1296,"sourceCodeEnd":1332,"githubUrl":"https://github.com/bumptech/glide/blob/eb14a895d8f866e6a08c3e19d50ea3bd2c12c20a/library/src/main/java/com/bumptech/glide/request/BaseRequestOptions.java#L1296-L1332","documentation":"Thrown by BaseRequestOptions.selfOrThrowIfLocked() whenever any mutator (centerCrop, placeholder, override, etc.) is called on a RequestOptions object whose isLocked flag is true and auto-clone is not enabled. Glide locks options once they have been applied to a live request so that mid-flight mutations cannot corrupt the in-progress load.","triggerScenarios":"Reusing a RequestOptions instance across two loads where the first load's apply()/into() locked it, then calling a setter on the same instance before the second load. Also reachable via RequestOptions that were cached in a field and mutated after first use.","commonSituations":"Storing RequestOptions in a companion/field for reuse and then calling .placeholder()/.error() conditionally per request; chaining a setter on the result of into() (which returns the Target, not options, but mis-assumptions cause reuse); mutating options returned by a RequestBuilder.","solutions":["Call .clone() before mutating: sharedOptions.clone().placeholder(drawable)","Build options fresh per load, or treat stored options as an immutable template and always clone-then-modify","If you want transparent cloning, enable autoClone() on a fresh unlocked instance before first use","Stop reusing the same RequestOptions instance across long-lived requests"],"exampleFix":"// before\nval opts = RequestOptions().centerCrop()\nfun bind(url: String, error: Drawable) {\n  opts.error(error) // throws on second call: opts locked after first load\n  Glide.with(this).load(url).apply(opts).into(iv)\n}\n\n// after\nval template = RequestOptions().centerCrop()\nfun bind(url: String, error: Drawable) {\n  Glide.with(this).load(url).apply(template.clone().error(error)).into(iv)\n}","handlingStrategy":"validation","validationCode":"fun RequestOptions.mutateSafe(block: RequestOptions.() -> Unit): RequestOptions =\n  clone().apply(block)","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Never mutate a RequestOptions after it has been applied to a request — clone first","Store RequestOptions as immutable templates, never as shared mutable state","Enable autoClone() once on a fresh instance if you want transparent copy-on-write"],"tags":["android","glide","immutability","state-machine","request-options"],"backgroundTag":null,"analyzedSha":"eb14a895d8f866e6a08c3e19d50ea3bd2c12c20a","analyzedAt":"2026-08-14T01:43:54.821Z","schemaVersion":2},"datasetVersion":"2026-08-14T05:17:29.042Z"}