Skip to content

Fix --check behavior when --dry-run is used#316

Open
ththicn wants to merge 1 commit intoz3z1ma:mainfrom
ththicn:fix-enable-check-with-dry-run
Open

Fix --check behavior when --dry-run is used#316
ththicn wants to merge 1 commit intoz3z1ma:mainfrom
ththicn:fix-enable-check-with-dry-run

Conversation

@ththicn
Copy link

@ththicn ththicn commented Feb 8, 2026

Hi maintainers, this is my first contribution, please let me know if anything should be changed in the approach, style, or tests. 🙏

When the --check flag was used with the --dry-run flag, the exit status was 0 even if there were changes in schema.yml. I made it so that mutation_tracker is called even when the --dry-run flag is passed.


Test

Preparation

Add a new column to the stg_orders model.

$ git diff demo_duckdb/models/staging/stg_orders.sql
diff --git a/demo_duckdb/models/staging/stg_orders.sql b/demo_duckdb/models/staging/stg_orders.sql
index a654dcb..bc0f31b 100644
--- a/demo_duckdb/models/staging/stg_orders.sql
+++ b/demo_duckdb/models/staging/stg_orders.sql
@@ -14,8 +14,8 @@ renamed as (
         id as order_id,
         user_id as customer_id,
         order_date,
-        status
-
+        status,
+        'new_column' as new_column
     from source

 )

Build the deme_duckdb project

$ uv run dbt build --project-dir ./demo_duckdb --profiles-dir ./demo_duckdb
07:04:06  Running with dbt=1.11.2
07:04:06  Registered adapter: duckdb=1.10.0
07:04:07  [WARNING][MissingArgumentsPropertyInGenericTestDeprecation]: Deprecated
functionality
Found top-level arguments to test `accepted_values` defined on 'stg_orders' in
package 'jaffle_shop_duckdb' (models/staging/jaffle_shop/main/stg_orders.yml).
Arguments to generic tests should be nested under the `arguments` property.
07:04:07  Found 7 models, 3 seeds, 22 data tests, 472 macros
07:04:07
07:04:07  Concurrency: 4 threads (target='dev')
07:04:07
07:04:07  1 of 32 START seed file main.raw_customers ..................................... [RUN]
07:04:07  2 of 32 START seed file main.raw_orders ........................................ [RUN]
07:04:07  3 of 32 START seed file main.raw_payments ...................................... [RUN]
07:04:07  1 of 32 OK loaded seed file main.raw_customers ................................. [INSERT 100 in 0.05s]
07:04:07  3 of 32 OK loaded seed file main.raw_payments .................................. [INSERT 113 in 0.05s]
07:04:07  2 of 32 OK loaded seed file main.raw_orders .................................... [INSERT 99 in 0.06s]
07:04:07  4 of 32 START sql view model main.stg_customers ................................ [RUN]
07:04:07  5 of 32 START sql view model main.stg_customers_v2 ............................. [RUN]
07:04:07  6 of 32 START sql view model main.stg_payments ................................. [RUN]
07:04:07  7 of 32 START sql view model main.stg_orders ................................... [RUN]
07:04:07  4 of 32 OK created sql view model main.stg_customers ........................... [OK in 0.07s]
07:04:07  6 of 32 OK created sql view model main.stg_payments ............................ [OK in 0.07s]
07:04:07  5 of 32 OK created sql view model main.stg_customers_v2 ........................ [OK in 0.07s]
07:04:07  7 of 32 OK created sql view model main.stg_orders .............................. [OK in 0.06s]
07:04:07  8 of 32 START test not_null_stg_customers_v1_customer_id ....................... [RUN]
07:04:07  9 of 32 START test unique_stg_customers_v1_customer_id ......................... [RUN]
07:04:07  10 of 32 START test accepted_values_stg_payments_payment_method__credit_card__coupon__bank_transfer__gift_card  [RUN]
07:04:07  11 of 32 START test not_null_stg_payments_payment_id ........................... [RUN]
07:04:07  11 of 32 PASS not_null_stg_payments_payment_id ................................. [PASS in 0.03s]
07:04:07  8 of 32 PASS not_null_stg_customers_v1_customer_id ............................. [PASS in 0.04s]
07:04:07  10 of 32 PASS accepted_values_stg_payments_payment_method__credit_card__coupon__bank_transfer__gift_card  [PASS in 0.04s]
07:04:07  9 of 32 PASS unique_stg_customers_v1_customer_id ............................... [PASS in 0.04s]
07:04:07  12 of 32 START test unique_stg_payments_payment_id ............................. [RUN]
07:04:07  13 of 32 START test not_null_stg_customers_v2_id ............................... [RUN]
07:04:07  14 of 32 START test unique_stg_customers_v2_id ................................. [RUN]
07:04:07  15 of 32 START test accepted_values_stg_orders_status__placed__shipped__completed__return_pending__returned  [RUN]
07:04:07  13 of 32 PASS not_null_stg_customers_v2_id ..................................... [PASS in 0.03s]
07:04:07  12 of 32 PASS unique_stg_payments_payment_id ................................... [PASS in 0.03s]
07:04:07  14 of 32 PASS unique_stg_customers_v2_id ....................................... [PASS in 0.03s]
07:04:07  15 of 32 PASS accepted_values_stg_orders_status__placed__shipped__completed__return_pending__returned  [PASS in 0.03s]
07:04:07  16 of 32 START test not_null_stg_orders_order_id ............................... [RUN]
07:04:07  17 of 32 START test unique_stg_orders_order_id ................................. [RUN]
07:04:07  16 of 32 PASS not_null_stg_orders_order_id ..................................... [PASS in 0.01s]
07:04:07  17 of 32 PASS unique_stg_orders_order_id ....................................... [PASS in 0.01s]
07:04:07  18 of 32 START sql table model main.customers .................................. [RUN]
07:04:07  19 of 32 START sql table model main.orders ..................................... [RUN]
07:04:07  20 of 32 START sql table model main.orders_prefix .............................. [RUN]
07:04:07  19 of 32 OK created sql table model main.orders ................................ [OK in 0.06s]
07:04:07  18 of 32 OK created sql table model main.customers ............................. [OK in 0.06s]
07:04:07  21 of 32 START test accepted_values_orders_status__placed__shipped__completed__return_pending__returned  [RUN]
07:04:07  22 of 32 START test not_null_orders_amount ..................................... [RUN]
07:04:07  23 of 32 START test not_null_orders_bank_transfer_amount ....................... [RUN]
07:04:07  20 of 32 OK created sql table model main.orders_prefix ......................... [OK in 0.06s]
07:04:07  24 of 32 START test not_null_orders_coupon_amount .............................. [RUN]
07:04:07  21 of 32 PASS accepted_values_orders_status__placed__shipped__completed__return_pending__returned  [PASS in 0.02s]
07:04:07  22 of 32 PASS not_null_orders_amount ........................................... [PASS in 0.02s]
07:04:07  25 of 32 START test not_null_orders_credit_card_amount ......................... [RUN]
07:04:07  26 of 32 START test not_null_orders_customer_id ................................ [RUN]
07:04:07  23 of 32 PASS not_null_orders_bank_transfer_amount ............................. [PASS in 0.03s]
07:04:07  24 of 32 PASS not_null_orders_coupon_amount .................................... [PASS in 0.02s]
07:04:07  27 of 32 START test not_null_orders_gift_card_amount ........................... [RUN]
07:04:07  28 of 32 START test not_null_orders_order_id ................................... [RUN]
07:04:07  25 of 32 PASS not_null_orders_credit_card_amount ............................... [PASS in 0.03s]
07:04:07  26 of 32 PASS not_null_orders_customer_id ...................................... [PASS in 0.03s]
07:04:07  29 of 32 START test unique_orders_order_id ..................................... [RUN]
07:04:07  27 of 32 PASS not_null_orders_gift_card_amount ................................. [PASS in 0.02s]
07:04:07  28 of 32 PASS not_null_orders_order_id ......................................... [PASS in 0.02s]
07:04:07  30 of 32 START test not_null_customers_customer_id ............................. [RUN]
07:04:07  31 of 32 START test relationships_orders_customer_id__customer_id__ref_customers_  [RUN]
07:04:07  32 of 32 START test unique_customers_customer_id ............................... [RUN]
07:04:07  30 of 32 PASS not_null_customers_customer_id ................................... [PASS in 0.03s]
07:04:07  29 of 32 PASS unique_orders_order_id ........................................... [PASS in 0.03s]
07:04:07  31 of 32 PASS relationships_orders_customer_id__customer_id__ref_customers_ .... [PASS in 0.03s]
07:04:07  32 of 32 PASS unique_customers_customer_id ..................................... [PASS in 0.03s]
07:04:07
07:04:07  Finished running 3 seeds, 3 table models, 22 data tests, 4 view models in 0 hours 0 minutes and 0.47 seconds (0.47s).
07:04:07
07:04:07  Completed successfully
07:04:07
07:04:07  Done. PASS=32 WARN=0 ERROR=0 SKIP=0 NO-OP=0 TOTAL=32
07:04:07  [WARNING][DeprecationsSummary]: Deprecated functionality
Summary of encountered deprecations:
- MissingArgumentsPropertyInGenericTestDeprecation: 1 occurrence
To see all deprecation instances instead of just the first occurrence of each,
run command again with the `--show-all-deprecations` flag. You may also need to
run with `--no-partial-parse` as some deprecations are only encountered during
parsing.

Testing dbt-osmosis

Before fixing

Changes exist, but exit status is 0.

INFO ➕ Reconciling missing column => new_column in node => model.jaffle_shop_duckdb.stg_orders > transforms.py:340

$ echo $?
0

$ uv run dbt-osmosis yaml refactor stg_orders --profiles-dir ./demo_duckdb/ --project-dir ./demo_duckdb --use-unrendered-descriptions --dry-run --check
INFO     🌊 Executing dbt-osmosis                                                                                                                                       main.py:343

INFO     👋 Creating DBT project context using config => DbtConfiguration(project_dir='./demo_duckdb', profiles_dir='./demo_duckdb/', target=None, profile=None,      config.py:514
         threads=None, single_threaded=None, vars={}, quiet=True, disable_introspection=False)
INFO     ✨ DbtProjectContext successfully created!                                                                                                                   config.py:566
INFO     📓 Osmosis ThreadPoolExecutor max_workers capped to dbt threads => 1                                                                                       settings.py:304
INFO     🏭 Creating missing source YAMLs and updating existing sources (if any).                                                                            path_management.py:234
INFO     💡 Drafting restructure delta plan for the project.                                                                                                   restructuring.py:158
INFO     🌐 Building YAML file mapping...                                                                                                                    path_management.py:193
INFO     🌟 Draft plan creation complete => 0 operations                                                                                                       restructuring.py:218
INFO     ✅ No changes needed in the restructure plan.                                                                                                         restructuring.py:283
INFO                                                                                                                                                              transforms.py:115
         ⚙ Running pipeline with => 5 operations ['Inject Missing Columns', 'Remove Extra Columns', 'Inherit Upstream Column Knowledge', 'Sort Columns',
         'Synchronize Data Types']

INFO     ⚙  Starting to Inject Missing Columns                                                                                                                    transforms.py:123
INFO     👋 Injecting missing columns for all matched nodes.                                                                                                      transforms.py:313
INFO     ⏳ Connection expired for thread => 6186135552, refreshing                                                                                                   config.py:356
INFO     🔎 Collecting columns for table => "jaffle_shop"."main"."stg_orders"                                                                                 introspection.py:1115
INFO     🔍 Introspecting columns in warehouse for => "jaffle_shop"."main"."stg_orders"                                                                       introspection.py:1184
INFO     ➕ Reconciling missing column => new_column in node => model.jaffle_shop_duckdb.stg_orders                                                               transforms.py:340
INFO     ✨ Done with Inject Missing Columns in 0.09s                                                                                                             transforms.py:130

INFO     ⚙  Starting to Remove Extra Columns                                                                                                                      transforms.py:123
INFO     👋 Removing columns not in DB across all matched nodes.                                                                                                  transforms.py:372
INFO     ✨ Done with Remove Extra Columns in 0.00s                                                                                                               transforms.py:130

INFO     ⚙  Starting to Inherit Upstream Column Knowledge                                                                                                         transforms.py:123
INFO     👋 Inheriting column knowledge across all matched nodes.                                                                                                 transforms.py:209
INFO     🧬 Inheriting column knowledge for => model.jaffle_shop_duckdb.stg_orders                                                                                transforms.py:225
INFO     ✨ Done with Inherit Upstream Column Knowledge in 0.01s                                                                                                  transforms.py:130

INFO     ⚙  Starting to Sort Columns                                                                                                                              transforms.py:123
INFO     👋 Sorting columns as configured across all matched nodes.                                                                                               transforms.py:491
INFO     🔢 Sorting columns by warehouse order => model.jaffle_shop_duckdb.stg_orders                                                                             transforms.py:417
INFO     ✨ Done with Sort Columns in 0.00s                                                                                                                       transforms.py:130

INFO     ⚙  Starting to Synchronize Data Types                                                                                                                    transforms.py:123
INFO     👋 Populating data types across all matched nodes.                                                                                                       transforms.py:521
INFO     🔢 Synchronizing data types => model.jaffle_shop_duckdb.stg_orders                                                                                       transforms.py:528
INFO     ✨ Done with Synchronize Data Types in 0.00s                                                                                                             transforms.py:130

INFO     🏁 Manifest transformation pipeline completed in => 0.11s                                                                                                transforms.py:150
INFO     ⌛ Committing all changes to YAML files in batch.                                                                                                        transforms.py:157
INFO     👋 No single node specified; synchronizing all matched nodes.                                                                                       sync_operations.py:558
INFO     📥 Committing YAML doc changes for => model.jaffle_shop_duckdb.stg_orders                                                                           sync_operations.py:504
INFO     🏁 YAML commits completed in => 0.00s                                                                                                                    transforms.py:164

$ echo $?
0

After fixing

$ uv run dbt-osmosis yaml refactor stg_orders --profiles-dir ./demo_duckdb/ --project-dir ./demo_duckdb --use-unrendered-descriptions --dry-run --check
INFO     🌊 Executing dbt-osmosis                                                                                                                                       main.py:343

INFO     👋 Creating DBT project context using config => DbtConfiguration(project_dir='./demo_duckdb', profiles_dir='./demo_duckdb/', target=None, profile=None,      config.py:514
         threads=None, single_threaded=None, vars={}, quiet=True, disable_introspection=False)
INFO     ✨ DbtProjectContext successfully created!                                                                                                                   config.py:566
INFO     📓 Osmosis ThreadPoolExecutor max_workers capped to dbt threads => 1                                                                                       settings.py:304
INFO     🏭 Creating missing source YAMLs and updating existing sources (if any).                                                                            path_management.py:234
INFO     💡 Drafting restructure delta plan for the project.                                                                                                   restructuring.py:158
INFO     🌐 Building YAML file mapping...                                                                                                                    path_management.py:193
INFO     🌟 Draft plan creation complete => 0 operations                                                                                                       restructuring.py:218
INFO     ✅ No changes needed in the restructure plan.                                                                                                         restructuring.py:283
INFO                                                                                                                                                              transforms.py:115
         ⚙ Running pipeline with => 5 operations ['Inject Missing Columns', 'Remove Extra Columns', 'Inherit Upstream Column Knowledge', 'Sort Columns',
         'Synchronize Data Types']

INFO     ⚙  Starting to Inject Missing Columns                                                                                                                    transforms.py:123
INFO     👋 Injecting missing columns for all matched nodes.                                                                                                      transforms.py:313
INFO     ⏳ Connection expired for thread => 6190641152, refreshing                                                                                                   config.py:356
INFO     🔎 Collecting columns for table => "jaffle_shop"."main"."stg_orders"                                                                                 introspection.py:1115
INFO     🔍 Introspecting columns in warehouse for => "jaffle_shop"."main"."stg_orders"                                                                       introspection.py:1184
INFO     ➕ Reconciling missing column => new_column in node => model.jaffle_shop_duckdb.stg_orders                                                               transforms.py:340
INFO     ✨ Done with Inject Missing Columns in 0.05s                                                                                                             transforms.py:130

INFO     ⚙  Starting to Remove Extra Columns                                                                                                                      transforms.py:123
INFO     👋 Removing columns not in DB across all matched nodes.                                                                                                  transforms.py:372
INFO     ✨ Done with Remove Extra Columns in 0.00s                                                                                                               transforms.py:130

INFO     ⚙  Starting to Inherit Upstream Column Knowledge                                                                                                         transforms.py:123
INFO     👋 Inheriting column knowledge across all matched nodes.                                                                                                 transforms.py:209
INFO     🧬 Inheriting column knowledge for => model.jaffle_shop_duckdb.stg_orders                                                                                transforms.py:225
INFO     ✨ Done with Inherit Upstream Column Knowledge in 0.01s                                                                                                  transforms.py:130

INFO     ⚙  Starting to Sort Columns                                                                                                                              transforms.py:123
INFO     👋 Sorting columns as configured across all matched nodes.                                                                                               transforms.py:491
INFO     🔢 Sorting columns by warehouse order => model.jaffle_shop_duckdb.stg_orders                                                                             transforms.py:417
INFO     ✨ Done with Sort Columns in 0.00s                                                                                                                       transforms.py:130

INFO     ⚙  Starting to Synchronize Data Types                                                                                                                    transforms.py:123
INFO     👋 Populating data types across all matched nodes.                                                                                                       transforms.py:521
INFO     🔢 Synchronizing data types => model.jaffle_shop_duckdb.stg_orders                                                                                       transforms.py:528
INFO     ✨ Done with Synchronize Data Types in 0.00s                                                                                                             transforms.py:130

INFO     🏁 Manifest transformation pipeline completed in => 0.07s                                                                                                transforms.py:150
INFO     ⌛ Committing all changes to YAML files in batch.                                                                                                        transforms.py:157
INFO     👋 No single node specified; synchronizing all matched nodes.                                                                                       sync_operations.py:558
INFO     📥 Committing YAML doc changes for => model.jaffle_shop_duckdb.stg_orders                                                                           sync_operations.py:504
INFO     👀 Would write changes to => demo_duckdb/models/staging/jaffle_shop/main/stg_orders.yml (dry-run)                                                            writer.py:125
INFO     🏁 YAML commits completed in => 0.00s                                                                                                                    transforms.py:164

$ echo $?
1

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant