infiniflow/ragflow · critical · ValueError
Invalid config file: "{global_config_path}".
Error message
Invalid config file: "{global_config_path}". What it means
ValueError raised by read_config in common/config_utils.py:66-69. The main configuration file conf/service_conf.yaml must be a YAML mapping at its root; if it parses to a list, scalar, or null (empty file parses to None, which is not a dict), startup aborts. Because CONFIGS = read_config() executes at import time of common.config_utils, every service entrypoint (API server, task executor) crashes on import when this fires.
Source
Thrown at common/config_utils.py:69
conf_path = f"conf/{conf_name}"
return os.path.join(get_project_base_directory(), conf_path)
def read_config(conf_name=SERVICE_CONF):
local_config = {}
local_path = conf_realpath(f"local.{conf_name}")
# load local config file
if os.path.exists(local_path):
local_config = load_yaml_conf(local_path)
if not isinstance(local_config, dict):
raise ValueError(f'Invalid config file: "{local_path}".')
global_config_path = conf_realpath(conf_name)
global_config = load_yaml_conf(global_config_path)
if not isinstance(global_config, dict):
raise ValueError(f'Invalid config file: "{global_config_path}".')
global_config.update(local_config)
return global_config
CONFIGS = read_config()
def show_configs():
msg = f"Current configs, from {conf_realpath(SERVICE_CONF)}:"
for k, v in CONFIGS.items():
if isinstance(v, dict):
if "password" in v:
v = copy.deepcopy(v)
v["password"] = "*" * 8
if "access_key" in v:
v = copy.deepcopy(v)
v["access_key"] = "*" * 8View on GitHub (pinned to 554fb1133a)
Solutions
- Fix conf/service_conf.yaml so the top level is key: value pairs only (no leading dashes, file not empty).
- Verify with: python -c "import yaml;d=yaml.safe_load(open('conf/service_conf.yaml'));print(type(d))" — must be <class 'dict'>.
- If the file is empty, restore it from git (git checkout -- conf/service_conf.yaml) and reapply your changes.
Example fix
# before: empty or list-rooted service_conf.yaml
- es:
hosts: es01:9200
# after
es:
hosts: es01:9200 Defensive patterns
Strategy: validation
Validate before calling
import yaml
with open("conf/service_conf.yaml") as f:
data = yaml.safe_load(f)
assert isinstance(data, dict), "service_conf.yaml root must be a mapping" Type guard
def is_valid_service_conf(path: str) -> bool:
import yaml
with open(path) as f:
return isinstance(yaml.safe_load(f), dict) Try / catch
try:
import common.config_utils
except ValueError as e:
if "Invalid config file" in str(e):
path = str(e).split('"')[1] # extract offending path from the message
restore_or_fix(path)
raise Prevention
- Add a startup preflight script validating all conf/*.yaml roots are dicts.
- Never commit an empty or list-rooted service_conf.yaml.
- Mount config files (not empty placeholders) in docker deployments.
When it happens
Trigger: Editing conf/service_conf.yaml so its root is not a mapping: top-level list items, a file containing only comments (parses to None), or a mangled/truncated file. Any process that imports common.config_utils then fails during startup.
Common situations: Bad merge or rebase leaving stray '- ' prefixes; template substitution leaving the file empty; hand-editing under time pressure and breaking indentation so the document root becomes a list; mounting an empty file over conf/service_conf.yaml in docker.
Related errors
- Invalid config file: "{local_path}".
- rewrite yaml file config {} failed:
- No private key
- Can't init admin.
- Invalid Tenki provider configuration.
AI-assisted analysis of infiniflow/ragflow@554fb1133a (2026-08-15).
Data as JSON: /api/errors/57c08ea1030bc7ed.
Report an issue: GitHub.