Referencing a YAML config file, from Python, when

2019-08-23 10:38发布

问题:

I have the following code;

#!/usr/bin/env python3

import yaml

with open('config.yml', 'r') as config_file:
    config = yaml.load(config_file)

The file is called __init__.py which is in the directory ~/bin/myprogram/myprogram/ and in the same directory, I have a file called config.yml

My symlink is as follows;

user$ ls -la /usr/local/bin/

lrwxr-xr-x    1 user  admin        55 27 Nov 13:25 myprogram -> /Users/user/bin/myprogram/myprogram/__init__.py

Every time I run myprogram, I get the error FileNotFoundError: [Errno 2] No such file or directory: 'config.yml'. I believe this is because the config.yml is not in /usr/local/bin/. What is the best way to work around this issue?

回答1:

You can use __file__ to access the location of the __init__.py file when executing code in that file. It returns the full path, but care has to be taken as it may be the .pyc (or .pyo) version. Since you are using Python3 I would use the pathlib module:

import yaml
import pathlib

my_path = Path(__file__).resolve()  # resolve to get rid of any symlinks
config_path = my_path.parent / 'config.yaml'

with config_path.open() as config_file:
    config = yaml.safe_load(config_file)

Please note:

  • If you have to use PyYAML, use safe_load(), even PyYAML's own documentation indicates .load() can be unsafe. It almost never necessary to use that. And in the unlikely event that safe_load() cannot load your config, e.g. if it has !!python/... tags, you should explicitly add register the classes that you actually need to the SafeLoader).

  • Since September 2006 the recommended extension for YAML files has been .yaml