Repository: dbt-labs/dbt-core

Issue:
[CT-1804] Add `--favor-state` as param in click CLI
Context: https://github.com/dbt-labs/dbt-core/pull/5859#discussion_r973083877


Discussion:
_Copying from https://github.com/dbt-labs/dbt-core/issues/6617_

### [Tech debt] Inconsistent implementation

Also, the way `--favor-state` was implemented is parallel to `--defer`, but different from most of our other flags since v1.0:

https://github.com/dbt-labs/dbt-core/blob/20c95a49933cd48dfbba9bd2ad5bc372ad440c6b/core/dbt/flags.py#L117-L118

(Namely, the argparse default is set based on the flag, rather than the other way around!)

https://github.com/dbt-labs/dbt-core/blob/20c95a49933cd48dfbba9bd2ad5bc372ad440c6b/core/dbt/main.py#L504-L515

Let's just solve for this when we move these flags/etc into the new CLI (#6585). We can always add back-compat for the older env vars + flag names — since, in the meantime, some users might add code to their projects like `{{ flags.FAVOR_STATE_MODE }}`.

Resolving patch:
diff --git a/core/dbt/cli/main.py b/core/dbt/cli/main.py
--- a/core/dbt/cli/main.py
+++ b/core/dbt/cli/main.py
@@ -103,6 +103,7 @@ def cli(ctx, **kwargs):
 @p.defer
 @p.exclude
 @p.fail_fast
+@p.favor_state
 @p.full_refresh
 @p.indirect_selection
 @p.profile
@@ -170,6 +171,7 @@ def docs(ctx, **kwargs):
 @p.compile_docs
 @p.defer
 @p.exclude
+@p.favor_state
 @p.models
 @p.profile
 @p.profiles_dir
@@ -233,6 +235,7 @@ def docs_serve(ctx, **kwargs):
 @click.pass_context
 @p.defer
 @p.exclude
+@p.favor_state
 @p.full_refresh
 @p.models
 @p.parse_only
@@ -401,6 +404,7 @@ def parse(ctx, **kwargs):
 @cli.command("run")
 @click.pass_context
 @p.defer
+@p.favor_state
 @p.exclude
 @p.fail_fast
 @p.full_refresh
@@ -503,6 +507,7 @@ def seed(ctx, **kwargs):
 @click.pass_context
 @p.defer
 @p.exclude
+@p.favor_state
 @p.models
 @p.profile
 @p.profiles_dir
@@ -583,6 +588,7 @@ def freshness(ctx, **kwargs):
 @p.defer
 @p.exclude
 @p.fail_fast
+@p.favor_state
 @p.indirect_selection
 @p.models
 @p.profile
diff --git a/core/dbt/cli/params.py b/core/dbt/cli/params.py
--- a/core/dbt/cli/params.py
+++ b/core/dbt/cli/params.py
@@ -92,6 +92,12 @@
     help="Stop execution on first failure.",
 )
 
+favor_state = click.option(
+    "--favor-state/--no-favor-state",
+    envvar="DBT_FAVOR_STATE",
+    help="If set, defer to the argument provided to the state flag for resolving unselected nodes, even if the node(s) exist as a database object in the current environment.",
+)
+
 full_refresh = click.option(
     "--full-refresh",
     "-f",


Test patch:
diff --git a/tests/functional/defer_state/test_defer_state.py b/tests/functional/defer_state/test_defer_state.py
--- a/tests/functional/defer_state/test_defer_state.py
+++ b/tests/functional/defer_state/test_defer_state.py
@@ -6,6 +6,7 @@
 import pytest
 
 from dbt.tests.util import run_dbt, write_file, rm_file
+from dbt.cli.main import dbtUsageException
 
 from dbt.exceptions import DbtRuntimeError
 
@@ -98,7 +99,7 @@ def run_and_save_state(self):
 class TestDeferStateUnsupportedCommands(BaseDeferState):
     def test_unsupported_commands(self, project):
         # make sure these commands don"t work with --defer
-        with pytest.raises(SystemExit):
+        with pytest.raises(dbtUsageException):
             run_dbt(["seed", "--defer"])
 
     def test_no_state(self, project):