Skip to content

Commit c832dc5

Browse files
authored
Fix insert_overwrite handling of schema update (#1058)
2 parents a9e2505 + 8ee37f6 commit c832dc5

4 files changed

Lines changed: 74 additions & 7 deletions

File tree

CHANGELOG.md

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,10 @@
1-
## dbt-databricks 1.10.3 (TBD)
1+
## dbt-databricks 1.10.4 (TBD)
2+
3+
### Fixes
4+
5+
- Fix bug where schema update causes insert_overwrite strategy to fail on subsequent runs ([1057](https://github.com/databricks/dbt-databricks/issues/1057))
6+
7+
## dbt-databricks 1.10.3 (June 4, 2025)
28

39
### Features
410

dbt/include/databricks/macros/materializations/incremental/strategies.sql

Lines changed: 13 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -25,15 +25,22 @@
2525
{{ return(get_insert_overwrite_sql(source, target)) }}
2626
{% endmacro %}
2727

28-
2928
{% macro get_insert_overwrite_sql(source_relation, target_relation) %}
30-
31-
{%- set dest_columns = adapter.get_columns_in_relation(target_relation) -%}
32-
{%- set dest_cols_csv = dest_columns | map(attribute='quoted') | join(', ') -%}
29+
{%- set dest_columns = adapter.get_columns_in_relation(target_relation) | map(attribute='quoted') | list -%}
30+
{%- set source_columns = adapter.get_columns_in_relation(source_relation) | map(attribute='quoted') | list -%}
31+
{%- set common_columns = [] -%}
32+
{%- for dest_col in dest_columns -%}
33+
{%- if dest_col in source_columns -%}
34+
{%- do common_columns.append(dest_col) -%}
35+
{%- else -%}
36+
{%- do common_columns.append('DEFAULT') -%}
37+
{%- endif -%}
38+
{%- endfor -%}
39+
{%- set dest_cols_csv = dest_columns | join(', ') -%}
40+
{%- set source_cols_csv = common_columns | join(', ') -%}
3341
insert overwrite table {{ target_relation }}
3442
{{ partition_cols(label="partition") }}
35-
select {{dest_cols_csv}} from {{ source_relation }}
36-
43+
select {{source_cols_csv}} from {{ source_relation }}
3744
{% endmacro %}
3845

3946
{% macro get_replace_where_sql(args_dict) -%}

tests/functional/adapter/incremental/fixtures.py

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -223,6 +223,12 @@
223223
3,anyway
224224
"""
225225

226+
upsert_expected_no_msg = """id,msg
227+
1,hello
228+
2,null
229+
3,null
230+
"""
231+
226232
upsert_expected = """id,msg
227233
1,hello
228234
2,yo
@@ -303,6 +309,26 @@
303309
{% endif %}
304310
"""
305311

312+
update_schema_model = """
313+
{{ config(
314+
materialized = 'incremental'
315+
) }}
316+
317+
{% if not is_incremental() %}
318+
319+
select cast(1 as bigint) as id, 'hello' as msg
320+
union all
321+
select cast(2 as bigint) as id, 'goodbye' as msg
322+
323+
{% else %}
324+
325+
select cast(2 as bigint) as id
326+
union all
327+
select cast(3 as bigint) as id
328+
329+
{% endif %}
330+
"""
331+
306332
upsert_model = """
307333
{{ config(
308334
materialized = 'incremental',

tests/functional/adapter/incremental/test_incremental_strategies.py

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -120,6 +120,34 @@ def test_incremental(self, project):
120120
util.check_relations_equal(project.adapter, ["overwrite_model", "upsert_expected"])
121121

122122

123+
@pytest.mark.skip_profile("databricks_uc_sql_endpoint")
124+
class TestInsertOverwriteChangeSchema(InsertOverwriteBase):
125+
@pytest.fixture(scope="class")
126+
def models(self):
127+
return {
128+
"overwrite_model.sql": fixtures.update_schema_model,
129+
}
130+
131+
@pytest.fixture(scope="class")
132+
def project_config_update(self):
133+
return {
134+
"models": {
135+
"+incremental_strategy": "insert_overwrite",
136+
"+partition_by": "id",
137+
},
138+
}
139+
140+
@pytest.fixture(scope="class")
141+
def seeds(self):
142+
return {
143+
"overwrite_expected.csv": fixtures.upsert_expected_no_msg,
144+
}
145+
146+
def test_incremental(self, project):
147+
self.seed_and_run_twice()
148+
util.check_relations_equal(project.adapter, ["overwrite_model", "overwrite_expected"])
149+
150+
123151
# Only runs under SQL warehouse profile, but overrides compute at model level
124152
@pytest.mark.skip_profile("databricks_uc_cluster", "databricks_cluster")
125153
class TestInsertOverwriteWithModelComputeOverride(IncrementalBase):

0 commit comments

Comments
 (0)