Coverage for src/mkdocs_manpage/config.py: 28.81%

43 statements  

« prev     ^ index     » next       coverage.py v7.2.7, created at 2023-06-05 21:04 +0200

1"""Configuration options for the MkDocs Manpage plugin.""" 

2 

3from __future__ import annotations 

4 

5import contextlib 

6from typing import Any, Dict, Generic, TypeVar 

7 

8from mkdocs.config import config_options as mkconf 

9from mkdocs.config.base import Config 

10from mkdocs.config.base import Config as BaseConfig 

11from mkdocs.config.config_options import BaseConfigOption, LegacyConfig, ValidationError 

12 

13T = TypeVar("T") 

14 

15 

16# TODO: remove once https://github.com/mkdocs/mkdocs/pull/3242 is merged and released 

17class DictOfItems(Generic[T], BaseConfigOption[Dict[str, T]]): 

18 """Validates a dict of items. Keys are always strings. 

19 

20 E.g. for `config_options.DictOfItems(config_options.Type(int))` a valid item is `{"a": 1, "b": 2}`. 

21 """ 

22 

23 required: bool | None = None # Only for subclasses to set. 

24 

25 def __init__(self, option_type: BaseConfigOption[T], default: Any = None) -> None: # noqa: D107 

26 super().__init__() 

27 self.default = default 

28 self.option_type = option_type 

29 self.option_type.warnings = self.warnings 

30 

31 def __repr__(self) -> str: 

32 return f"{type(self).__name__}: {self.option_type}" 

33 

34 def pre_validation(self, config: Config, key_name: str) -> None: # noqa: D102 

35 self._config = config 

36 self._key_name = key_name 

37 

38 def run_validation(self, value: object) -> dict[str, T]: # noqa: D102 

39 if value is None: 

40 if self.required or self.default is None: 

41 raise ValidationError("Required configuration not provided.") 

42 value = self.default 

43 if not isinstance(value, dict): 

44 raise ValidationError(f"Expected a dict of items, but a {type(value)} was given.") 

45 if not value: # Optimization for empty list 

46 return value 

47 

48 fake_config = LegacyConfig(()) 

49 with contextlib.suppress(AttributeError): 

50 fake_config.config_file_path = self._config.config_file_path 

51 

52 # Emulate a config-like environment for pre_validation and post_validation. 

53 fake_config.data = value 

54 

55 for key_name in fake_config: 

56 self.option_type.pre_validation(fake_config, key_name) 

57 for key_name in fake_config: 

58 # Specifically not running `validate` to avoid the OptionallyRequired effect. 

59 fake_config[key_name] = self.option_type.run_validation(fake_config[key_name]) 

60 for key_name in fake_config: 

61 self.option_type.post_validation(fake_config, key_name) 

62 

63 return value 

64 

65 

66class PluginConfig(BaseConfig): 

67 """Configuration options for the plugin.""" 

68 

69 enabled = mkconf.Type(bool, default=True) 

70 pages = mkconf.ListOfItems(mkconf.Type(str))