azure-dbx-job-update

CAN_MANAGE on a Databricks job allows updating the job task definition (notebook, JAR, wheel, script, DLT pipeline), injecting attacker code.

derived azure emits CanModifyCode

match (effective permission)

{ "action": "databricks:jobs:update", "scope_type": "job" }

where

principal has Databricks CAN_MANAGE permission on the target job (POST /api/2.1/jobs/update) job task is a notebook, JAR, wheel, Python script, or DLT pipeline reference

emit

source typeIdentity
source<principal>
target<Databricks Job (BatchJob)>
permissionsdatabricks:jobs:update (CAN_MANAGE on the job — POST /api/2.1/jobs/update)
conditionstrigger_exists

Narrative

{principal.name} can update the task definition of Databricks job {target.name} (CAN_MANAGE, /api/2.1/jobs/update), injecting attacker code that runs as the job cluster's managed identity on next execution.

Raw rule rules/derived/azure/databricks.yaml

id: azure-dbx-job-update
emits: CanModifyCode
description: CAN_MANAGE on a Databricks job allows updating the job task definition (notebook, JAR, wheel,
  script, DLT pipeline), injecting attacker code.
match_effective_permission:
  action: databricks:jobs:update
  scope_type: job
where:
- principal has Databricks CAN_MANAGE permission on the target job (POST /api/2.1/jobs/update)
- job task is a notebook, JAR, wheel, Python script, or DLT pipeline reference
emit:
  source_type: Identity
  source: <principal>
  target: <Databricks Job (BatchJob)>
  permissions:
  - "databricks:jobs:update (CAN_MANAGE on the job \u2014 POST /api/2.1/jobs/update)"
  conditions:
  - trigger_exists
  escalation: Update the job task (notebook path, JAR location, wheel, or Python script) to point at attacker-controlled
    code; on next scheduled or on-demand run the job executes as the job cluster's Access Connector MI.
    Mirrors cicd-chains cicd-modify-buildspec-executes-as (job runner = BuildWorker, definition = task
    spec).
  false_positive_note: "CAN_MANAGE_RUN does NOT allow task update \u2014 only CAN_MANAGE (job owner/admin)\
    \ does. CAN_MANAGE_RUN gives trigger-only ability (run-now), not code modification; use cicd-chains\
    \ cicd-trigger-runner-executes-as for that weaker path. If the job has no schedule and no trigger,\
    \ CONDITIONAL(trigger_exists)."
  narrative: '{principal.name} can update the task definition of Databricks job {target.name} (CAN_MANAGE,
    /api/2.1/jobs/update), injecting attacker code that runs as the job cluster''s managed identity on
    next execution.'
move · open · esc close