{"record":{"id":"c41ebe0aa57e473e","repo":"immich-app/immich","slug":"cannot-update-configuration-while-immich-config-fi","errorCode":null,"errorMessage":"Cannot update configuration while IMMICH_CONFIG_FILE is in use","messagePattern":"Cannot update configuration while IMMICH_CONFIG_FILE is in use","errorType":"exception","errorClass":"BadRequestException","httpStatus":400,"severity":"error","filePath":"server/src/services/system-config.service.ts","lineNumber":87,"sourceCode":"\n  @OnEvent({ name: 'ConfigUpdate', server: true })\n  onConfigUpdate({ newConfig }: ArgOf<'ConfigUpdate'>) {\n    this.onConfigInit({ newConfig });\n    clearConfigCache();\n  }\n\n  @OnEvent({ name: 'ConfigValidate' })\n  onConfigValidate({ newConfig, oldConfig }: ArgOf<'ConfigValidate'>) {\n    const { logLevel } = this.configRepository.getEnv();\n    if (logLevel && !isEqual(toPlainObject(newConfig.logging), oldConfig.logging)) {\n      throw new Error('Logging cannot be changed while the environment variable IMMICH_LOG_LEVEL is set.');\n    }\n  }\n\n  async updateAdminConfig(dto: AdminConfigDto): Promise<AdminConfigDto> {\n    const { configFile } = this.configRepository.getEnv();\n    if (configFile) {\n      throw new BadRequestException('Cannot update configuration while IMMICH_CONFIG_FILE is in use');\n    }\n\n    const oldConfig = await this.getConfig({ withCache: false });\n\n    try {\n      await this.eventRepository.emit('ConfigValidate', { newConfig: toPlainObject(dto), oldConfig });\n    } catch (error) {\n      this.logger.warn(`Unable to save system config due to a validation error: ${error}`);\n      throw new BadRequestException(error instanceof Error ? error.message : error);\n    }\n\n    const newConfig = await this.updateConfig(dto);\n\n    await this.eventRepository.emit('ConfigUpdate', { newConfig, oldConfig });\n\n    return mapAdminConfig(newConfig);\n  }\n","sourceCodeStart":69,"sourceCodeEnd":105,"githubUrl":"https://github.com/immich-app/immich/blob/e55ac299a4ec7cb372e35dbf2c6c05ee9ce77f6c/server/src/services/system-config.service.ts#L69-L105","documentation":"When IMMICH_CONFIG_FILE points at a config file, the runtime configuration is managed by that file and is read-only through the API. updateAdminConfig throws BadRequestException to prevent drift between the file and the stored database config.","triggerScenarios":"Any admin UI or API attempt to save system config while IMMICH_CONFIG_FILE env var is set in the server environment.","commonSituations":"Deployments pinned by a config file where an admin edits settings in the web UI; teams switching from file-based to DB-based config without removing the env var.","solutions":["Remove the IMMICH_CONFIG_FILE environment variable and restart the server, then manage config via the UI/API","Edit the referenced config file directly instead of using the admin UI","Keep the admin UI read-only for config while file-based config is in use"],"exampleFix":"// before\nenvironment:\n  IMMICH_CONFIG_FILE: /config/immich.json\n// admin UI save -> error\n// after\nenvironment: {}\n// manage config via admin UI, or edit /config/immich.json directly","handlingStrategy":"validation","validationCode":"if (process.env.IMMICH_CONFIG_FILE) throw new Error('Runtime config is read-only: IMMICH_CONFIG_FILE is set');","typeGuard":"null","tryCatchPattern":"try {\n  await saveAdminConfig(dto);\n} catch (e) {\n  if (e.status === 400 && e.message.includes('IMMICH_CONFIG_FILE')) {\n    // persist changes to the config file instead, or ask operator to unset the env var\n  }\n}","preventionTips":["Pick one config management mode: file or admin UI","Hide/disable config editing in the UI when IMMICH_CONFIG_FILE is set","Edit the config file directly in file-based deployments"],"tags":["config","env-var","read-only","bad-request"],"backgroundTag":"conflicting-config-options","analyzedSha":"e55ac299a4ec7cb372e35dbf2c6c05ee9ce77f6c","analyzedAt":"2026-09-15T07:20:19.675Z","contentChangedAt":"2026-09-15T07:20:19.675Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}