Edit on GitHub

sqlmesh.dbt.profile

  1from __future__ import annotations
  2
  3import logging
  4import os
  5import typing as t
  6from pathlib import Path
  7
  8from sqlmesh.dbt.common import PROJECT_FILENAME, load_yaml
  9from sqlmesh.dbt.context import DbtContext
 10from sqlmesh.dbt.target import TargetConfig
 11from sqlmesh.utils import yaml
 12from sqlmesh.utils.errors import ConfigError
 13
 14logger = logging.getLogger(__name__)
 15
 16
 17class Profile:
 18    """
 19    A class to read DBT profiles and obtain the project's target data warehouse configuration
 20    """
 21
 22    PROFILE_FILE = "profiles.yml"
 23
 24    def __init__(
 25        self,
 26        path: Path,
 27        target_name: str,
 28        target: TargetConfig,
 29    ):
 30        """
 31        Args:
 32            path: Path to the profile file
 33            target_name: Name of the target loaded
 34            target: TargetConfig for target_name
 35        """
 36        self.path = path
 37        self.target_name = target_name
 38        self.target = target
 39
 40    @classmethod
 41    def load(cls, context: DbtContext, target_name: t.Optional[str] = None) -> Profile:
 42        """
 43        Loads the profile for the specified project
 44
 45        Args:
 46            context: DBT context for this profile
 47
 48        Returns:
 49            The Profile for the specified project
 50        """
 51        if not context.profile_name:
 52            project_file = Path(context.project_root, PROJECT_FILENAME)
 53            if not project_file.exists():
 54                raise ConfigError(f"Could not find {PROJECT_FILENAME} in {context.project_root}")
 55
 56            project_yaml = load_yaml(project_file)
 57            context.profile_name = context.render(
 58                project_yaml.get("profile", "")
 59            ) or context.render(project_yaml.get("name", ""))
 60            if not context.profile_name:
 61                raise ConfigError(f"{project_file.stem} must include project name.")
 62
 63        profile_filepath = cls._find_profile(context.project_root, context.profiles_dir)
 64        if not profile_filepath:
 65            raise ConfigError(f"{cls.PROFILE_FILE} not found.")
 66
 67        target_name, target = cls._read_profile(profile_filepath, context, target_name)
 68        return Profile(profile_filepath, target_name, target)
 69
 70    @classmethod
 71    def _find_profile(cls, project_root: Path, profiles_dir: t.Optional[Path]) -> t.Optional[Path]:
 72        dir = os.environ.get("DBT_PROFILES_DIR", profiles_dir or "")
 73        path = Path(project_root, dir, cls.PROFILE_FILE)
 74        if path.exists():
 75            return path
 76        if dir:
 77            return None
 78
 79        path = Path(Path.home(), ".dbt", cls.PROFILE_FILE)
 80        if path.exists():
 81            return path
 82
 83        return None
 84
 85    @classmethod
 86    def _read_profile(
 87        cls, path: Path, context: DbtContext, target_name: t.Optional[str] = None
 88    ) -> t.Tuple[str, TargetConfig]:
 89        logger.debug("Processing profile '%s'.", path)
 90        project_data = load_yaml(path).get(context.profile_name)
 91        if not project_data:
 92            raise ConfigError(f"Profile '{context.profile_name}' not found in profiles.")
 93
 94        outputs = project_data.get("outputs")
 95        if not outputs:
 96            raise ConfigError(f"No outputs exist in profiles for '{context.profile_name}'.")
 97
 98        if not target_name:
 99            if "target" not in project_data:
100                raise ConfigError(f"No target specified for '{context.profile_name}'.")
101            target_name = context.render(project_data.get("target"))
102
103        if target_name not in outputs:
104            target_names = "\n".join(f"- {name}" for name in outputs)
105            raise ConfigError(
106                f"Target '{target_name}' not specified in profiles for '{context.profile_name}'. "
107                f"The valid target names for this profile are:\n{target_names}"
108            )
109
110        target_fields = load_yaml(context.render(yaml.dump(outputs[target_name])))
111        target = TargetConfig.load(
112            {"name": target_name, "profile_name": context.profile_name, **target_fields}
113        )
114
115        return (target_name, target)
logger = <Logger sqlmesh.dbt.profile (WARNING)>
class Profile:
 18class Profile:
 19    """
 20    A class to read DBT profiles and obtain the project's target data warehouse configuration
 21    """
 22
 23    PROFILE_FILE = "profiles.yml"
 24
 25    def __init__(
 26        self,
 27        path: Path,
 28        target_name: str,
 29        target: TargetConfig,
 30    ):
 31        """
 32        Args:
 33            path: Path to the profile file
 34            target_name: Name of the target loaded
 35            target: TargetConfig for target_name
 36        """
 37        self.path = path
 38        self.target_name = target_name
 39        self.target = target
 40
 41    @classmethod
 42    def load(cls, context: DbtContext, target_name: t.Optional[str] = None) -> Profile:
 43        """
 44        Loads the profile for the specified project
 45
 46        Args:
 47            context: DBT context for this profile
 48
 49        Returns:
 50            The Profile for the specified project
 51        """
 52        if not context.profile_name:
 53            project_file = Path(context.project_root, PROJECT_FILENAME)
 54            if not project_file.exists():
 55                raise ConfigError(f"Could not find {PROJECT_FILENAME} in {context.project_root}")
 56
 57            project_yaml = load_yaml(project_file)
 58            context.profile_name = context.render(
 59                project_yaml.get("profile", "")
 60            ) or context.render(project_yaml.get("name", ""))
 61            if not context.profile_name:
 62                raise ConfigError(f"{project_file.stem} must include project name.")
 63
 64        profile_filepath = cls._find_profile(context.project_root, context.profiles_dir)
 65        if not profile_filepath:
 66            raise ConfigError(f"{cls.PROFILE_FILE} not found.")
 67
 68        target_name, target = cls._read_profile(profile_filepath, context, target_name)
 69        return Profile(profile_filepath, target_name, target)
 70
 71    @classmethod
 72    def _find_profile(cls, project_root: Path, profiles_dir: t.Optional[Path]) -> t.Optional[Path]:
 73        dir = os.environ.get("DBT_PROFILES_DIR", profiles_dir or "")
 74        path = Path(project_root, dir, cls.PROFILE_FILE)
 75        if path.exists():
 76            return path
 77        if dir:
 78            return None
 79
 80        path = Path(Path.home(), ".dbt", cls.PROFILE_FILE)
 81        if path.exists():
 82            return path
 83
 84        return None
 85
 86    @classmethod
 87    def _read_profile(
 88        cls, path: Path, context: DbtContext, target_name: t.Optional[str] = None
 89    ) -> t.Tuple[str, TargetConfig]:
 90        logger.debug("Processing profile '%s'.", path)
 91        project_data = load_yaml(path).get(context.profile_name)
 92        if not project_data:
 93            raise ConfigError(f"Profile '{context.profile_name}' not found in profiles.")
 94
 95        outputs = project_data.get("outputs")
 96        if not outputs:
 97            raise ConfigError(f"No outputs exist in profiles for '{context.profile_name}'.")
 98
 99        if not target_name:
100            if "target" not in project_data:
101                raise ConfigError(f"No target specified for '{context.profile_name}'.")
102            target_name = context.render(project_data.get("target"))
103
104        if target_name not in outputs:
105            target_names = "\n".join(f"- {name}" for name in outputs)
106            raise ConfigError(
107                f"Target '{target_name}' not specified in profiles for '{context.profile_name}'. "
108                f"The valid target names for this profile are:\n{target_names}"
109            )
110
111        target_fields = load_yaml(context.render(yaml.dump(outputs[target_name])))
112        target = TargetConfig.load(
113            {"name": target_name, "profile_name": context.profile_name, **target_fields}
114        )
115
116        return (target_name, target)

A class to read DBT profiles and obtain the project's target data warehouse configuration

Profile( path: pathlib.Path, target_name: str, target: sqlmesh.dbt.target.TargetConfig)
25    def __init__(
26        self,
27        path: Path,
28        target_name: str,
29        target: TargetConfig,
30    ):
31        """
32        Args:
33            path: Path to the profile file
34            target_name: Name of the target loaded
35            target: TargetConfig for target_name
36        """
37        self.path = path
38        self.target_name = target_name
39        self.target = target
Arguments:
  • path: Path to the profile file
  • target_name: Name of the target loaded
  • target: TargetConfig for target_name
PROFILE_FILE = 'profiles.yml'
path
target_name
target
@classmethod
def load( cls, context: sqlmesh.dbt.context.DbtContext, target_name: Optional[str] = None) -> Profile:
41    @classmethod
42    def load(cls, context: DbtContext, target_name: t.Optional[str] = None) -> Profile:
43        """
44        Loads the profile for the specified project
45
46        Args:
47            context: DBT context for this profile
48
49        Returns:
50            The Profile for the specified project
51        """
52        if not context.profile_name:
53            project_file = Path(context.project_root, PROJECT_FILENAME)
54            if not project_file.exists():
55                raise ConfigError(f"Could not find {PROJECT_FILENAME} in {context.project_root}")
56
57            project_yaml = load_yaml(project_file)
58            context.profile_name = context.render(
59                project_yaml.get("profile", "")
60            ) or context.render(project_yaml.get("name", ""))
61            if not context.profile_name:
62                raise ConfigError(f"{project_file.stem} must include project name.")
63
64        profile_filepath = cls._find_profile(context.project_root, context.profiles_dir)
65        if not profile_filepath:
66            raise ConfigError(f"{cls.PROFILE_FILE} not found.")
67
68        target_name, target = cls._read_profile(profile_filepath, context, target_name)
69        return Profile(profile_filepath, target_name, target)

Loads the profile for the specified project

Arguments:
  • context: DBT context for this profile
Returns:

The Profile for the specified project