fatedier/frp · error
failed to create store source: %w
Error message
failed to create store source: %w
What it means
The client store feature is enabled (common.store) but source.NewStoreSource failed while preparing the on-disk cache at the resolved store path. The path is joined with the config file's directory when relative, so failure usually means the filesystem location is unusable.
Source
Thrown at cmd/frpc/sub/root.go:155
func runClientWithAggregator(result *config.ClientConfigLoadResult, unsafeFeatures *security.UnsafeFeatures, cfgFilePath string) error {
configSource := source.NewConfigSource()
if err := configSource.ReplaceAll(result.Proxies, result.Visitors); err != nil {
return fmt.Errorf("failed to set config source: %w", err)
}
var storeSource *source.StoreSource
if result.Common.Store.IsEnabled() {
storePath := result.Common.Store.Path
if storePath != "" && cfgFilePath != "" && !filepath.IsAbs(storePath) {
storePath = filepath.Join(filepath.Dir(cfgFilePath), storePath)
}
s, err := source.NewStoreSource(source.StoreSourceConfig{
Path: storePath,
})
if err != nil {
return fmt.Errorf("failed to create store source: %w", err)
}
storeSource = s
}
aggregator := source.NewAggregator(configSource)
if storeSource != nil {
aggregator.SetStoreSource(storeSource)
}
proxyCfgs, visitorCfgs, err := aggregator.Load()
if err != nil {
return fmt.Errorf("failed to load config from sources: %w", err)
}
proxyCfgs, visitorCfgs = config.FilterClientConfigurers(result.Common, proxyCfgs, visitorCfgs)
proxyCfgs = config.CompleteProxyConfigurers(proxyCfgs)
visitorCfgs = config.CompleteVisitorConfigurers(visitorCfgs)
View on GitHub (pinned to 6c8a8d0a97)
Solutions
- Check the resolved store path: if relative it joins filepath.Dir(cfgFile); confirm the directory exists and frpc can write to it.
- Fix permissions or pre-create the directory, or point store.path to an absolute writable location.
- If a stale or corrupt cache file is the cause (parse error inside), delete it; the store is a cache and will be rebuilt.
- If you don't need offline config caching, disable common.store.
Example fix
# before (frpc.toml) [store] enabled = true path = "/var/frpc/cache" # parent dir missing # after [store] enabled = true path = "/var/frpc/cache/frpc_cache" # mkdir -p /var/frpc/cache first
Defensive patterns
Strategy: validation
Validate before calling
if result.Common.Store.IsEnabled() {
p := result.Common.Store.Path
if !filepath.IsAbs(p) {
p = filepath.Join(filepath.Dir(cfgFilePath), p)
}
if f, err := os.OpenFile(p, os.O_RDWR|os.O_CREATE, 0o600); err != nil {
return fmt.Errorf("store path not writable: %w", err)
} else {
f.Close()
}
} Prevention
- Use absolute store paths in service deployments
- Pre-create and permission the store directory for the frpc user
- Container setups: mount a writable volume at the store path
When it happens
Trigger: NewStoreSource errors on an unwritable or nonexistent directory for the store file, a path that exists but has wrong type or permissions, or an unparsable existing store file at that path.
Common situations: store.path points to a location frpc cannot write (read-only volume, missing directory, permissions); relative store.path resolved against an unexpected cfgFile directory; a corrupted or hand-edited cache file from a previous version.
Related errors
- ErrAlreadyExists
- failed to load config from sources: %w
- include: parse directory of %s failed: %v
- include: directory of %s not exist
- path is required
AI-assisted analysis of fatedier/frp@6c8a8d0a97 (2026-08-15).
Data as JSON: /api/errors/e11090d27b6e463d.
Report an issue: GitHub.