Skip to content

Commit 94d066e

Browse files
bundle/direct: conditionally upgrade state version when opted into DMS
Normal deploys keep writing state_version 2. When the bundle opts into experimental.record_deployment_history, the deploy upgrades the local state to dmsStateVersion (3) and stamps a new CurrentDmsVersion header field, so future DMS breaking changes or minimum-CLI requirements can be gated on what the state was written with. migrateState now reads up to dmsStateVersion but still auto-migrates only up to the baseline currentStateVersion, so a v3 state is neither auto-applied nor downgraded. The upgrade is applied explicitly in deployCore, never as an automatic migration. Co-authored-by: Isaac
1 parent 30db14f commit 94d066e

23 files changed

Lines changed: 417 additions & 35 deletions

File tree

acceptance/acceptance_test.go

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -277,6 +277,13 @@ func testAccept(t *testing.T, inprocessMode bool, singleTest string) int {
277277
cli293Path := DownloadCLI(t, buildDir, "0.293.0")
278278
t.Setenv("CLI_293", cli293Path)
279279
repls.SetPath(cli293Path, "[CLI_293]")
280+
281+
// v1.0.0 understands state schema versions only up to 2. Used by tests
282+
// asserting that an older CLI rejects newer state (e.g. the v3 state
283+
// written when a bundle opts into the deployment metadata service).
284+
cliV1Path := DownloadCLI(t, buildDir, "1.0.0")
285+
t.Setenv("CLI_V1", cliV1Path)
286+
repls.SetPath(cliV1Path, "[CLI_V1]")
280287
}
281288

282289
paths := []string{
Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
bundle:
2+
name: test-rdh-state-upgrade
3+
4+
experimental:
5+
record_deployment_history: true
6+
7+
resources:
8+
jobs:
9+
foo:
10+
name: foo-job-renamed
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
bundle:
2+
name: test-rdh-state-upgrade
3+
4+
resources:
5+
jobs:
6+
foo:
7+
name: foo-job

acceptance/bundle/deploy/record-deployment-history/state-upgrade/out.test.toml

Lines changed: 3 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.
Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
2+
=== without the flag: state stays at the baseline schema version
3+
>>> [CLI] bundle deploy
4+
Uploading bundle files to /Workspace/Users/[USERNAME]/.bundle/test-rdh-state-upgrade/default/files...
5+
Deploying resources...
6+
Updating deployment state...
7+
Deployment complete!
8+
9+
>>> print_state.py
10+
{
11+
"state_version": 2,
12+
"dms_version": null
13+
}
14+
15+
=== with experimental.record_deployment_history: state upgrades and records the DMS version
16+
>>> [CLI] bundle deploy
17+
Uploading bundle files to /Workspace/Users/[USERNAME]/.bundle/test-rdh-state-upgrade/default/files...
18+
Deploying resources...
19+
Updating deployment state...
20+
Deployment complete!
21+
22+
>>> print_state.py
23+
{
24+
"state_version": 3,
25+
"dms_version": 1
26+
}
27+
28+
=== an older CLI (v1.0.0, max state version 2) rejects operations on the upgraded state
29+
>>> errcode [CLI_V1] bundle plan
30+
Warning: unknown field: record_deployment_history
31+
at experimental
32+
in databricks.yml:5:3
33+
34+
Error: migrating state [TEST_TMP_DIR]/.databricks/bundle/default/resources.json: state version 3 is newer than supported version 2; upgrade the CLI
35+
36+
37+
Exit code: 1
38+
39+
=== with the flag, a state written by a newer record_deployment_history version is rejected
40+
>>> update_file.py .databricks/bundle/default/resources.json "dms_version": 1 "dms_version": 2
41+
42+
>>> errcode [CLI] bundle plan
43+
Error: record_deployment_history state version 2 is newer than supported version 1; upgrade the CLI
44+
45+
46+
Exit code: 1
47+
48+
=== without the flag, the same state is accepted (the check is gated on opt-in)
49+
>>> update_file.py databricks.yml record_deployment_history: true record_deployment_history: false
50+
51+
>>> errcode [CLI] bundle plan
52+
Plan: 0 to add, 0 to change, 0 to delete, 1 unchanged
Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
# State-version lifecycle for the DMS preview (experimental.record_deployment_history):
2+
# 1. Without the flag, deploys keep writing the baseline state version.
3+
# 2. Opting in upgrades the state version and records the DMS version.
4+
# 3. An older CLI that predates the DMS state version refuses to operate on the
5+
# upgraded state and tells the user to upgrade, so it cannot mishandle it.
6+
# 4. With the flag set, a state stamped with a newer record_deployment_history
7+
# version than this CLI knows is also refused (the state schema version is
8+
# one we support). Without the flag the check is skipped.
9+
10+
title "without the flag: state stays at the baseline schema version"
11+
trace $CLI bundle deploy
12+
trace print_state.py | jq '{state_version, dms_version}'
13+
14+
title "with experimental.record_deployment_history: state upgrades and records the DMS version"
15+
# Also renames the job so the deploy writes state (a no-op deploy would not
16+
# rewrite the state file and the upgrade would not be observable yet).
17+
cp databricks.dms.yml databricks.yml
18+
trace $CLI bundle deploy
19+
trace print_state.py | jq '{state_version, dms_version}'
20+
21+
title "an older CLI (v1.0.0, max state version 2) rejects operations on the upgraded state"
22+
trace errcode $CLI_V1 bundle plan 2>&1 | contains.py "state version 3 is newer than supported version 2; upgrade the CLI"
23+
24+
title "with the flag, a state written by a newer record_deployment_history version is rejected"
25+
# The state must hold a record_deployment_history version greater than this CLI's
26+
# supported version (currentDmsVersion) to be rejected, so we set supported+1.
27+
# TODO: when currentDmsVersion is bumped, change the value written below to the new
28+
# supported+1. The error's version numbers are not asserted here, so the assertion
29+
# needs no change.
30+
trace update_file.py .databricks/bundle/default/resources.json '"dms_version": 1' '"dms_version": 2'
31+
trace errcode $CLI bundle plan 2>&1 | contains.py "record_deployment_history state version" "is newer than supported version" "upgrade the CLI"
32+
33+
title "without the flag, the same state is accepted (the check is gated on opt-in)"
34+
trace update_file.py databricks.yml "record_deployment_history: true" "record_deployment_history: false"
35+
trace errcode $CLI bundle plan 2>&1 | contains.py "!is newer than supported version"
Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
Local = true
2+
Cloud = false
3+
4+
# databricks.yml is rewritten in-place by the script (flag added in the second step).
5+
Ignore = [".databricks", "databricks.yml"]
6+
7+
# The state-version upgrade only applies to the direct engine; terraform stores
8+
# state differently and would diverge.
9+
[EnvMatrix]
10+
DATABRICKS_BUNDLE_ENGINE = ["direct"]
Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
bundle:
2+
name: test-rdh-terraform-unsupported
3+
4+
experimental:
5+
record_deployment_history: true
6+
7+
resources:
8+
jobs:
9+
foo:
10+
name: foo-job

acceptance/bundle/deploy/record-deployment-history/terraform-unsupported/out.test.toml

Lines changed: 3 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.
Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
2+
>>> errcode [CLI] bundle plan
3+
Error: experimental.record_deployment_history is only supported with the direct deployment engine
4+
5+
6+
Exit code: 1

0 commit comments

Comments
 (0)