yaml_utils.py 1.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051
  1. """YAML utilities"""
  2. from __future__ import annotations
  3. import typing
  4. import yaml
  5. from apispec.utils import dedent, trim_docstring
  6. def dict_to_yaml(dic: dict, yaml_dump_kwargs: typing.Any | None = None) -> str:
  7. """Serializes a dictionary to YAML."""
  8. yaml_dump_kwargs = yaml_dump_kwargs or {}
  9. # By default, don't sort alphabetically to respect schema field ordering
  10. yaml_dump_kwargs.setdefault("sort_keys", False)
  11. return yaml.dump(dic, **yaml_dump_kwargs)
  12. def load_yaml_from_docstring(docstring: str) -> dict:
  13. """Loads YAML from docstring."""
  14. split_lines = trim_docstring(docstring).split("\n")
  15. # Cut YAML from rest of docstring
  16. for index, line in enumerate(split_lines):
  17. line = line.strip()
  18. if line.startswith("---"):
  19. cut_from = index
  20. break
  21. else:
  22. return {}
  23. yaml_string = "\n".join(split_lines[cut_from:])
  24. yaml_string = dedent(yaml_string)
  25. return yaml.safe_load(yaml_string) or {}
  26. PATH_KEYS = {"get", "put", "post", "delete", "options", "head", "patch"}
  27. def load_operations_from_docstring(docstring: str) -> dict:
  28. """Return a dictionary of OpenAPI operations parsed from a
  29. a docstring.
  30. """
  31. doc_data = load_yaml_from_docstring(docstring)
  32. return {
  33. key: val
  34. for key, val in doc_data.items()
  35. if key in PATH_KEYS or key.startswith("x-")
  36. }