mirror of
https://github.com/Stone-Red-Code/dvc.git
synced 2026-11-05 23:09:32 +01:00
cli: config: add support for --show-origin (#5126)
* cli: config: add support for --show-origin Support the --show-origin option for config, which, similar to git, prefixes each config option with the source file it originated from. Fixes #5119 * Reformat with black. * Simplify logic for local config files. * Add test for --show-config output. * Update tests/func/test_config.py Co-authored-by: Ruslan Kuprieiev <[email protected]>
This commit is contained in:
co-authored by
Ruslan Kuprieiev
parent
23811e028c
commit
34ed545d64
+40
-4
@@ -1,8 +1,10 @@
|
||||
import argparse
|
||||
import logging
|
||||
import os
|
||||
|
||||
from dvc.command.base import CmdBaseNoRepo, append_doc_link
|
||||
from dvc.config import Config, ConfigError
|
||||
from dvc.repo import Repo
|
||||
from dvc.utils.flatten import flatten
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
@@ -34,6 +36,14 @@ class CmdConfig(CmdBaseNoRepo):
|
||||
self.config = Config(validate=False)
|
||||
|
||||
def run(self):
|
||||
if self.args.show_origin:
|
||||
if any((self.args.value, self.args.unset)):
|
||||
logger.error(
|
||||
"--show-origin can't be used together with any of these "
|
||||
"options: -u/--unset, value"
|
||||
)
|
||||
return 1
|
||||
|
||||
if self.args.list:
|
||||
if any((self.args.name, self.args.value, self.args.unset)):
|
||||
logger.error(
|
||||
@@ -43,7 +53,11 @@ class CmdConfig(CmdBaseNoRepo):
|
||||
return 1
|
||||
|
||||
conf = self.config.load_one(self.args.level)
|
||||
logger.info("\n".join(self._format_config(conf)))
|
||||
prefix = self._config_file_prefix(
|
||||
self.args.show_origin, self.config, self.args.level
|
||||
)
|
||||
|
||||
logger.info("\n".join(self._format_config(conf, prefix)))
|
||||
return 0
|
||||
|
||||
if self.args.name is None:
|
||||
@@ -54,10 +68,14 @@ class CmdConfig(CmdBaseNoRepo):
|
||||
|
||||
if self.args.value is None and not self.args.unset:
|
||||
conf = self.config.load_one(self.args.level)
|
||||
prefix = self._config_file_prefix(
|
||||
self.args.show_origin, self.config, self.args.level
|
||||
)
|
||||
|
||||
if remote:
|
||||
conf = conf["remote"]
|
||||
self._check(conf, remote, section, opt)
|
||||
logger.info(conf[section][opt])
|
||||
logger.info("{}{}".format(prefix, conf[section][opt]))
|
||||
return 0
|
||||
|
||||
with self.config.edit(self.args.level) as conf:
|
||||
@@ -90,9 +108,21 @@ class CmdConfig(CmdBaseNoRepo):
|
||||
)
|
||||
|
||||
@staticmethod
|
||||
def _format_config(config):
|
||||
def _format_config(config, prefix=""):
|
||||
for key, value in flatten(config).items():
|
||||
yield f"{key}={value}"
|
||||
yield f"{prefix}{key}={value}"
|
||||
|
||||
@staticmethod
|
||||
def _config_file_prefix(show_origin, config, level):
|
||||
if not show_origin:
|
||||
return ""
|
||||
|
||||
fname = config.files[level]
|
||||
|
||||
if level in ["local", "repo"]:
|
||||
fname = os.path.relpath(fname, start=Repo.find_root())
|
||||
|
||||
return fname + "\t"
|
||||
|
||||
|
||||
parent_config_parser = argparse.ArgumentParser(add_help=False)
|
||||
@@ -152,4 +182,10 @@ def add_parser(subparsers, parent_parser):
|
||||
action="store_true",
|
||||
help="List all defined config values.",
|
||||
)
|
||||
config_parser.add_argument(
|
||||
"--show-origin",
|
||||
default=False,
|
||||
action="store_true",
|
||||
help="Show the source file containing each config value.",
|
||||
)
|
||||
config_parser.set_defaults(func=CmdConfig)
|
||||
|
||||
@@ -48,9 +48,15 @@ class TestConfigCLI(TestDvc):
|
||||
self.assertEqual(ret, 0)
|
||||
self.assertTrue(self._contains(section, field, value, local))
|
||||
|
||||
ret = main(base + [section_field, value, "--show-origin"])
|
||||
self.assertEqual(ret, 1)
|
||||
|
||||
ret = main(base + [section_field])
|
||||
self.assertEqual(ret, 0)
|
||||
|
||||
ret = main(base + ["--show-origin", section_field])
|
||||
self.assertEqual(ret, 0)
|
||||
|
||||
ret = main(base + [section_field, newvalue])
|
||||
self.assertEqual(ret, 0)
|
||||
self.assertTrue(self._contains(section, field, newvalue, local))
|
||||
@@ -60,9 +66,15 @@ class TestConfigCLI(TestDvc):
|
||||
self.assertEqual(ret, 0)
|
||||
self.assertFalse(self._contains(section, field, value, local))
|
||||
|
||||
ret = main(base + [section_field, "--unset", "--show-origin"])
|
||||
self.assertEqual(ret, 1)
|
||||
|
||||
ret = main(base + ["--list"])
|
||||
self.assertEqual(ret, 0)
|
||||
|
||||
ret = main(base + ["--list", "--show-origin"])
|
||||
self.assertEqual(ret, 0)
|
||||
|
||||
def test(self):
|
||||
self._do_test(False)
|
||||
|
||||
@@ -174,3 +186,28 @@ def test_config_remote(tmp_dir, dvc, caplog):
|
||||
caplog.clear()
|
||||
assert main(["config", "remote.myremote.region"]) == 0
|
||||
assert "myregion" in caplog.text
|
||||
|
||||
|
||||
def test_config_show_origin(tmp_dir, dvc, caplog):
|
||||
(tmp_dir / ".dvc" / "config").write_text(
|
||||
"['remote \"myremote\"']\n"
|
||||
" url = s3://bucket/path\n"
|
||||
" region = myregion\n"
|
||||
)
|
||||
|
||||
caplog.clear()
|
||||
assert main(["config", "--show-origin", "remote.myremote.url"]) == 0
|
||||
assert (
|
||||
"{}\t{}\n".format(os.path.join(".dvc", "config"), "s3://bucket/path")
|
||||
in caplog.text
|
||||
)
|
||||
|
||||
caplog.clear()
|
||||
assert main(["config", "--list", "--show-origin"]) == 0
|
||||
assert (
|
||||
"{}\t{}\n".format(
|
||||
os.path.join(".dvc", "config"),
|
||||
"remote.myremote.url=s3://bucket/path",
|
||||
)
|
||||
in caplog.text
|
||||
)
|
||||
|
||||
Reference in New Issue
Block a user