Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Cloud = false
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@

=== A second login for the same profile replaces the first

>>> [CLI] auth login --host [DATABRICKS_URL] --profile test --use-device-code

>>> [CLI] auth login --host [DATABRICKS_URL] --profile test --use-device-code

>>> update_file.py home/.databricks/token-cache.json WDJBMJHT NEWRCODE

>>> cache_keys
[
"test#device-code"
]

>>> musterr [CLI] auth login --host [DATABRICKS_URL] --profile test --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
Error: a newer login for profile test replaced this one. Complete the newer login with its user code. Run the same command without --user-code and --confirmation-code to start a new login

>>> [CLI] auth login --host [DATABRICKS_URL] --profile test --use-device-code --user-code NEWR-CODE --confirmation-code FTFA-QQKY
Profile test was successfully saved

>>> print_requests.py --oneline //oidc/v1/token
{"method": "POST", "path": "/oidc/v1/token", "raw_body": "client_id=databricks-cli&confirmation_code=FTFAQQKY&device_code=device-code-2&grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Adevice_code"}

=== Logins for different targets are independent

>>> [CLI] auth login --host [DATABRICKS_URL] --profile a --use-device-code

>>> [CLI] auth login --host [DATABRICKS_URL] --profile b --use-device-code

>>> [CLI] auth login --host [DATABRICKS_URL] --use-device-code

>>> cache_keys
[
"a#device-code",
"b#device-code",
"[DATABRICKS_URL]",
"[DATABRICKS_URL]#device-code",
"test"
]

>>> [CLI] auth login --host [DATABRICKS_URL] --profile b --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
Profile b was successfully saved

>>> [CLI] auth login --host [DATABRICKS_URL] --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY

>>> [CLI] auth login --host [DATABRICKS_URL] --profile a --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
Profile a was successfully saved

>>> cache_keys
[
"a",
"b",
"[DATABRICKS_URL]",
"test"
]

>>> print_requests.py --oneline //oidc/v1/token
{"method": "POST", "path": "/oidc/v1/token", "raw_body": "client_id=databricks-cli&confirmation_code=FTFAQQKY&device_code=device-code-4&grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Adevice_code"}
{"method": "POST", "path": "/oidc/v1/token", "raw_body": "client_id=databricks-cli&confirmation_code=FTFAQQKY&device_code=device-code-5&grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Adevice_code"}
{"method": "POST", "path": "/oidc/v1/token", "raw_body": "client_id=databricks-cli&confirmation_code=FTFAQQKY&device_code=device-code-3&grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Adevice_code"}
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
sethome "./home"

# The real server issues a new user code for every login, while the fake server
# issues the same one. The script gives the second login its own user code.
title "A second login for the same profile replaces the first\n"
start_login LOG.first $CLI auth login --host $DATABRICKS_HOST --profile test --use-device-code
start_login LOG.second $CLI auth login --host $DATABRICKS_HOST --profile test --use-device-code
trace update_file.py home/.databricks/token-cache.json WDJBMJHT NEWRCODE
trace cache_keys
trace musterr $CLI auth login --host $DATABRICKS_HOST --profile test --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
trace $CLI auth login --host $DATABRICKS_HOST --profile test --use-device-code --user-code NEWR-CODE --confirmation-code FTFA-QQKY
trace print_requests.py --oneline //oidc/v1/token

title "Logins for different targets are independent\n"
start_login LOG.a $CLI auth login --host $DATABRICKS_HOST --profile a --use-device-code
start_login LOG.b $CLI auth login --host $DATABRICKS_HOST --profile b --use-device-code
start_login LOG.host $CLI auth login --host $DATABRICKS_HOST --use-device-code
trace cache_keys
trace $CLI auth login --host $DATABRICKS_HOST --profile b --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
trace $CLI auth login --host $DATABRICKS_HOST --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
trace $CLI auth login --host $DATABRICKS_HOST --profile a --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
trace cache_keys
trace print_requests.py --oneline //oidc/v1/token
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
[resources]
host = $DATABRICKS_HOST
resources = https://resource.test
auth_type = databricks-cli
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Cloud = false
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@

=== Device code login is disabled by default

>>> musterr [CLI] auth login --host [DATABRICKS_URL] --profile test --use-device-code
Error: --use-device-code is experimental. Set DATABRICKS_CLI_DEVICE_CODE=true to enable it

>>> musterr [CLI] auth login --host [DATABRICKS_URL] --profile test --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
Error: --use-device-code is experimental. Set DATABRICKS_CLI_DEVICE_CODE=true to enable it

=== Flags the non-interactive login cannot honor

>>> musterr [CLI] auth login --host [DATABRICKS_URL] --profile test --use-device-code --configure-cluster
Error: --configure-cluster is not supported by the non-interactive device code login. Set cluster_id on the profile after the login

=== Missing host

>>> musterr [CLI] auth login --use-device-code
Error: --use-device-code requires a workspace host. Pass it as an argument or with --host

>>> musterr [CLI] auth login --profile test --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
Error: --use-device-code requires a workspace host. Pass it as an argument or with --host

=== Incomplete flags of the second step

>>> musterr [CLI] auth login --host [DATABRICKS_URL] --profile test --use-device-code --confirmation-code FTFA-QQKY
Error: --confirmation-code requires --user-code

>>> musterr [CLI] auth login --host [DATABRICKS_URL] --profile test --use-device-code --user-code WDJB-MJHT
Error: --user-code requires --confirmation-code

>>> musterr [CLI] auth login --host [DATABRICKS_URL] --profile test --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
Error: --confirmation-code requires --use-device-code

=== Account host

>>> musterr [CLI] auth login --host https://accounts.cloud.databricks.test --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
Warn: [hostmetadata] failed to fetch host metadata for https://accounts.cloud.databricks.test, will skip for 1m0s
Error: --use-device-code is only supported for workspace hosts

=== Profile scoped to resources

>>> musterr [CLI] auth login --profile resources --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
Error: --use-device-code cannot be used with profile resources because its login is scoped to resources. Log in without --use-device-code

=== No pending login

>>> musterr [CLI] auth login --host [DATABRICKS_URL] --profile test --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
Error: no pending device code login for profile test. Run the same command without --user-code and --confirmation-code to start a new login

>>> musterr [CLI] auth login --host [DATABRICKS_URL] --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
Error: no pending device code login for host [DATABRICKS_URL]. Run the same command without --user-code and --confirmation-code to start a new login

>>> [CLI] auth login --host [DATABRICKS_URL] --profile test --use-device-code

=== Wrong confirmation code

>>> musterr [CLI] auth login --host [DATABRICKS_URL] --profile test --use-device-code --user-code WDJB-MJHT --confirmation-code AAAA-AAAA
Error: token exchange: Invalid confirmation code (error code: invalid_request). Check the confirmation code and approve the login if you haven't, then rerun this command. Run the same command without --user-code and --confirmation-code to start a new login if it still fails

=== Rerun with the right confirmation code

>>> [CLI] auth login --host [DATABRICKS_URL] --profile test --use-device-code --user-code wdjb-mjht --confirmation-code ftfa-qqky
Profile test was successfully saved

=== Rerun after the login was completed

>>> musterr [CLI] auth login --host [DATABRICKS_URL] --profile test --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
Error: no pending device code login for profile test. Run the same command without --user-code and --confirmation-code to start a new login

=== Device code unknown to the server

>>> [CLI] auth login --host [DATABRICKS_URL] --profile test --use-device-code

>>> update_file.py home/.databricks/token-cache.json device-code-2 unknown-device-code

>>> musterr [CLI] auth login --host [DATABRICKS_URL] --profile test --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
Error: token exchange: Invalid device code (error code: invalid_request). Run the same command without --user-code and --confirmation-code to start a new login

>>> cache_keys
[
"[DATABRICKS_URL]",
"test"
]

>>> print_requests.py --oneline //oidc/v1/device/auth //oidc/v1/token
{"method": "POST", "path": "/oidc/v1/device/auth", "raw_body": "client_id=databricks-cli&scope=offline_access+all-apis"}
{"method": "POST", "path": "/oidc/v1/token", "raw_body": "client_id=databricks-cli&confirmation_code=AAAAAAAA&device_code=device-code-1&grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Adevice_code"}
{"method": "POST", "path": "/oidc/v1/token", "raw_body": "client_id=databricks-cli&confirmation_code=FTFAQQKY&device_code=device-code-1&grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Adevice_code"}
{"method": "POST", "path": "/oidc/v1/device/auth", "raw_body": "client_id=databricks-cli&scope=offline_access+all-apis"}
{"method": "POST", "path": "/oidc/v1/token", "raw_body": "client_id=databricks-cli&confirmation_code=FTFAQQKY&device_code=unknown-device-code&grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Adevice_code"}
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
sethome "./home"

title "Device code login is disabled by default\n"
(
unset DATABRICKS_CLI_DEVICE_CODE
trace musterr $CLI auth login --host $DATABRICKS_HOST --profile test --use-device-code
trace musterr $CLI auth login --host $DATABRICKS_HOST --profile test --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
)

title "Flags the non-interactive login cannot honor\n"
trace musterr $CLI auth login --host $DATABRICKS_HOST --profile test --use-device-code --configure-cluster

# The non-interactive login cannot answer the profile picker or the host prompt.
title "Missing host\n"
trace musterr $CLI auth login --use-device-code
trace musterr $CLI auth login --profile test --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY

title "Incomplete flags of the second step\n"
trace musterr $CLI auth login --host $DATABRICKS_HOST --profile test --use-device-code --confirmation-code FTFA-QQKY
trace musterr $CLI auth login --host $DATABRICKS_HOST --profile test --use-device-code --user-code WDJB-MJHT
trace musterr $CLI auth login --host $DATABRICKS_HOST --profile test --user-code WDJB-MJHT --confirmation-code FTFA-QQKY

title "Account host\n"
trace musterr $CLI auth login --host https://accounts.cloud.databricks.test --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY

envsubst < "./home/.databrickscfg.tmpl" > "./home/.databrickscfg"

title "Profile scoped to resources\n"
trace musterr $CLI auth login --profile resources --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY

title "No pending login\n"
trace musterr $CLI auth login --host $DATABRICKS_HOST --profile test --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
trace musterr $CLI auth login --host $DATABRICKS_HOST --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY

start_login LOG.wrong-code $CLI auth login --host $DATABRICKS_HOST --profile test --use-device-code

title "Wrong confirmation code\n"
trace musterr $CLI auth login --host $DATABRICKS_HOST --profile test --use-device-code --user-code WDJB-MJHT --confirmation-code AAAA-AAAA

# A wrong confirmation code leaves the device code valid, so the pending
# login is kept.
title "Rerun with the right confirmation code\n"
trace $CLI auth login --host $DATABRICKS_HOST --profile test --use-device-code --user-code wdjb-mjht --confirmation-code ftfa-qqky

title "Rerun after the login was completed\n"
trace musterr $CLI auth login --host $DATABRICKS_HOST --profile test --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY

# The server discards the device code when the login expires. The pending
# login is then deleted.
title "Device code unknown to the server\n"
start_login LOG.expired $CLI auth login --host $DATABRICKS_HOST --profile test --use-device-code
trace update_file.py home/.databricks/token-cache.json device-code-2 unknown-device-code
trace musterr $CLI auth login --host $DATABRICKS_HOST --profile test --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
trace cache_keys

trace print_requests.py --oneline //oidc/v1/device/auth //oidc/v1/token
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
[scoped]
host = $DATABRICKS_HOST
scopes = sql
client_id = databricks-cli
auth_type = databricks-cli
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
; The profile defined in the DEFAULT section is to be used as a fallback when no profile is explicitly specified.
[DEFAULT]

[scoped]
host = [DATABRICKS_URL]
scopes = sql
auth_type = databricks-cli
workspace_id = [WORKSPACE_ID]
client_id = databricks-cli

[serverless]
host = [DATABRICKS_URL]
serverless_compute_id = auto
workspace_id = [WORKSPACE_ID]
auth_type = databricks-cli
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Cloud = false
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@

=== Scopes and client ID from the profile

>>> [CLI] auth login --profile scoped --use-device-code
Using a browser on another device, visit:
[DATABRICKS_URL]/device/verification

And enter the code:
WDJB-MJHT

Once finished, complete the login by running the same command with
--user-code WDJB-MJHT and --confirmation-code set to the confirmation code
provided in your browser.

>>> [CLI] auth login --profile scoped --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
Profile scoped was successfully saved

>>> print_requests.py --oneline //oidc/v1/device/auth //oidc/v1/token
{"method": "POST", "path": "/oidc/v1/device/auth", "raw_body": "client_id=databricks-cli&scope=offline_access+sql"}
{"method": "POST", "path": "/oidc/v1/token", "raw_body": "client_id=databricks-cli&confirmation_code=FTFAQQKY&device_code=device-code-1&grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Adevice_code"}

=== Serverless compute is configured in the second step

>>> [CLI] auth login --host [DATABRICKS_URL] --profile serverless --use-device-code --configure-serverless
Using a browser on another device, visit:
[DATABRICKS_URL]/device/verification

And enter the code:
WDJB-MJHT

Once finished, complete the login by running the same command with
--user-code WDJB-MJHT and --confirmation-code set to the confirmation code
provided in your browser.

>>> [CLI] auth login --host [DATABRICKS_URL] --profile serverless --use-device-code --configure-serverless --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
Profile serverless was successfully saved
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
sethome "./home"
envsubst < "./home/.databrickscfg.tmpl" > "./home/.databrickscfg"

# The rerun resolves the login from the same flags and profile as the first
# step, so the token exchange uses the client ID of the profile.
title "Scopes and client ID from the profile\n"
trace $CLI auth login --profile scoped --use-device-code
trace $CLI auth login --profile scoped --use-device-code --user-code WDJB-MJHT --confirmation-code FTFA-QQKY
trace print_requests.py --oneline //oidc/v1/device/auth //oidc/v1/token

# Only the second step saves the profile.
title "Serverless compute is configured in the second step\n"
trace $CLI auth login --host $DATABRICKS_HOST --profile serverless --use-device-code --configure-serverless
trace $CLI auth login --host $DATABRICKS_HOST --profile serverless --use-device-code --configure-serverless --user-code WDJB-MJHT --confirmation-code FTFA-QQKY

mv "./home/.databrickscfg" "./out.databrickscfg"
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
; The profile defined in the DEFAULT section is to be used as a fallback when no profile is explicitly specified.
[DEFAULT]

[test]
host = [DATABRICKS_URL]
workspace_id = [WORKSPACE_ID]
auth_type = databricks-cli

[__settings__]
default_profile = test
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Cloud = false
Loading
Loading