{"record":{"id":"5ff9361f7875a47d","repo":"fatedier/frp","slug":"reload-config-from-sources-failed-w","errorCode":null,"errorMessage":"reload config from sources failed: %w","messagePattern":"reload config from sources failed: %w","errorType":"console","errorClass":null,"httpStatus":null,"severity":"error","filePath":"client/service.go","lineNumber":508,"sourceCode":"func (svr *Service) reloadConfigFromSources() error {\n\tsvr.reloadMu.Lock()\n\tdefer svr.reloadMu.Unlock()\n\treturn svr.reloadConfigFromSourcesLocked()\n}\n\nfunc (svr *Service) reloadConfigFromSourcesLocked() error {\n\taggregator := svr.aggregator\n\tif aggregator == nil {\n\t\treturn errors.New(\"config aggregator is not initialized\")\n\t}\n\n\tsvr.cfgMu.RLock()\n\treloadCommon := svr.reloadCommon\n\tsvr.cfgMu.RUnlock()\n\n\tproxies, visitors, err := aggregator.Load()\n\tif err != nil {\n\t\treturn fmt.Errorf(\"reload config from sources failed: %w\", err)\n\t}\n\n\tproxies, visitors = config.FilterClientConfigurers(reloadCommon, proxies, visitors)\n\tproxies = config.CompleteProxyConfigurers(proxies)\n\tvisitors = config.CompleteVisitorConfigurers(visitors)\n\trequirements := validation.GetClientConfigRequirements(reloadCommon, proxies, visitors)\n\tif svr.vnetController == nil && requirements.VirtualNet {\n\t\treturn errors.New(\n\t\t\t\"VirtualNet-dependent configuration requires a VirtualNet runtime enabled at startup; \" +\n\t\t\t\t\"restart frpc after configuring featureGates.VirtualNet and virtualNet.address\",\n\t\t)\n\t}\n\n\t// Atomically replace the entire configuration\n\tif err := svr.UpdateAllConfigurer(proxies, visitors); err != nil {\n\t\treturn err\n\t}\n\treturn nil","sourceCodeStart":490,"sourceCodeEnd":526,"githubUrl":"https://github.com/fatedier/frp/blob/6c8a8d0a97d03b44e9528d30b30c70cb9d61b405/client/service.go#L490-L526","documentation":"Returned by reloadConfigFromSourcesLocked when the config aggregator's Load() fails during a config reload (frpc reload / API-triggered reload). Unlike startup, frpc is already running; the reload is aborted and the existing proxies keep running with the previous configuration.","triggerScenarios":"Editing a config source (file or included fragment) into an invalid state and then triggering reload; a watched file being unreadable mid-write; an include disappearing between startup and reload.","commonSituations":"Hot-reloading after a partial edit (editor write in progress); broken TOML introduced by sed/script automation; include files removed but still referenced.","solutions":["Check the wrapped error for the failing source and line number of the parse failure.","Fix the config file syntax and run frpc verify -c frpc.toml before retrying the reload.","Make edits atomically (write temp file + rename) so reload never sees a half-written file.","Note the running config is unchanged — no need to restart unless you want the failed changes forced."],"exampleFix":"# before: reload after breaking the file\n# [[proxies]  (missing closing brackets)\n\n# after: fix syntax, verify, then reload\n# [[proxies]]\n#   name = \"ssh\"\nfrpc verify -c frpc.toml && frpc reload -c frpc.toml","handlingStrategy":"validation","validationCode":"// Validate before reload: parse the file exactly as frpc will\n// shell: frpc verify -c frpc.toml && frpc reload -c frpc.toml","typeGuard":null,"tryCatchPattern":"if err := svr.ReloadConfig(); err != nil {\n    if strings.Contains(err.Error(), \"reload config from sources\") {\n        log.Warnf(\"reload aborted, running with previous config: %v\", err)\n        // safe to keep serving; fix file and reload again\n    }\n}","preventionTips":["Always frpc verify before frpc reload.","Edit files atomically so watchers never read partial writes.","Keep previous good configs for quick rollback."],"tags":["config","reload","frpc","parse-error"],"backgroundTag":null,"analyzedSha":"6c8a8d0a97d03b44e9528d30b30c70cb9d61b405","analyzedAt":"2026-08-15T06:53:27.215Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}