Dev.to Security πŸ” Cybersecurity πŸ‘ 0 πŸ“– 5 min read

Controlling Databricks Costs with Cluster Policies and Tagging

Giving data scientists and engineers direct access to create clusters is the fastest way to turn a cloud budget into a smoking crater. Most platforms attempt to solve this with "process"β€”asking users to check a box or fo

Controlling Databricks Costs with Cluster Policies and Tagging

Giving data scientists and engineers direct access to create clusters is the fastest way to turn a cloud budget into a smoking crater. Most platforms attempt to solve this with "process"β€”asking users to check a box or follow a naming conventionβ€”but manual governance in distributed systems is a fantasy that fails the moment a deadline approaches.

If you aren't using Databricks Cluster Policies to constrain the compute environment, you aren't managing costs; you are merely witnessing them.

The contenders

The choice here is between unrestricted cluster creation (the default state) and policy-based enforcement.

Unrestricted creation allows maximum flexibility, letting users pick any instance type, runtime version, or library configuration. In environments where "move fast" is the only directive, this leads to massive instances being spun up for trivial tasks and forgotten when the notebook session closes.

Cluster Policies, conversely, act as a schema for cluster creation. When a user creates a cluster via the UI or API, the policy acts as a gatekeeper. It can force specific configurations, hide dangerous options, or mandate tags. You are moving from a "please play nice" culture to a "the system prevents you from doing otherwise" architecture.

a close-up of a green leaf
Photo by Nika Benedictova on Unsplash

Cost and resource constraints

At the level of the Spark driver and executor, cluster policy is your primary tool for enforcing resource limits. You can use the spark_conf attribute in a policy to force specific configurations or set absolute maximums for instance types.

Consider an illustrative scenario where you want to prevent users from accidentally selecting memory-optimized instances for a simple ETL job. You can define a policy that restricts the node_type_id to a specific list of general-purpose instances.

{
  "node_type_id": {
    "type": "fixed",
    "value": "Standard_DS3_v2"
  },
  "autotermination_minutes": {
    "type": "fixed",
    "value": 30
  }
}

By forcing the autotermination_minutes to 30, you ensure that even if a user forgets to shut down their cluster after a job runs, the platform terminates the compute automatically. This is a mechanism that operates at the cloud provider level (e.g., terminating the VM instances) rather than just pausing the Spark application.

Enforcing organizational accountability with tags

In regulated industries, knowing exactly which cost center or project owns a specific cluster isn't just about accounting; it's a security and audit requirement. Databricks policies allow you to force the inclusion of custom tags.

If you don't enforce tags via policy, they will be missing. It is that simple. By using the custom_tags attribute in a cluster policy, you can mandate that users provide a ProjectID or CostCenter before they are even allowed to click "Create Cluster."

{
  "custom_tags.ProjectID": {
    "type": "unlimited"
  },
  "custom_tags.Environment": {
    "type": "fixed",
    "value": "production"
  }
}

When a user attempts to create a cluster using this policy, the API will reject the request if the ProjectID tag is missing. This pushes the data quality of your billing logs to the point of origin, ensuring that cloud provider invoices are sliced by tag without needing a separate, error-prone manual reconciliation process.

Operational burden and failure modes

The primary failure mode of implementing cluster policies is "policy drift" or being overly restrictive. If you lock down the spark_version to a specific runtime that hits end-of-life, every cluster creation request will fail simultaneously.

Policies require maintenance. You must treat them as code. If you define your policies through the Databricks UI, you lose the ability to version control your governance strategy. I recommend managing these policies via Terraform using the databricks_cluster_policy resource. This allows you to peer-review changes to your infrastructure governance just like you would review a change to a PySpark transformation.

Another failure mode is the "permission trap." If you remove the canUse permission from a user or service principal, their existing automated jobsβ€”if they rely on that policyβ€”will fail to start during their next run. Always test policy updates in a staging workspace before applying them to a production environment.

Comparison Summary

Feature Unrestricted Policy-Enforced
Cost Control None Hard limits via instance type/autoterm
Billing Accuracy Relies on user input Mandatory tagging enforcement
Ops Burden Low initially Requires lifecycle management
User Experience High freedom Context-specific guardrails

a computer screen with a bunch of data on it
Photo by Justin Morgan on Unsplash

How to measure it yourself

To see the impact of your policy, you don't need a massive cluster. You can observe the policy mechanism locally by simulating a request to the Databricks Clusters API.

  1. Create a policy in your workspace.
  2. Use the Databricks CLI or a Python script with the databricks-sdk to attempt to create a cluster that violates your policy.
from databricks.sdk import WorkspaceClient
from databricks.sdk.service import compute

w = WorkspaceClient()

# Attempt to create a cluster with a policy ID that forces a 30-min timeout
# and a specific node type.
try:
    w.clusters.create(
        cluster_name="test-policy-violation",
        spark_version="13.3.x-scala2.12",
        node_type_id="Standard_F4s_v2", # Assuming policy forbids this
        policy_id="<your-policy-id>",
        autotermination_minutes=120 # Assuming policy forbids this
    )
except Exception as e:
    print(f"Policy successfully blocked the request: {e}")

If the API returns a 400 Bad Request related to policy validation, your guardrails are working. If the cluster spins up, your policy is either not applied to your user or is too permissive.

What I'd pick, and why

I always default to mandatory policies. The argument that policies "slow down" developers is usually a symptom of poorly designed policies rather than the concept of policies itself.

If you design your policies to be "self-service" (e.g., a "Data Science" policy that allows slightly more memory but forces cost tags, and an "ETL" policy that is rigid and cheap), developers won't feel shackled. They will feel supported because they don't have to guess what configuration is "correct."

Avoid the temptation to create a "catch-all" policy. That leads to bloat and makes it impossible to update configurations without risking a workspace-wide outage. Instead, create a hierarchy of policies mapped to specific user personas or workloads.

The goal isn't to stop people from doing data work; it’s to ensure that when they do that work, the platform is configured to be reliable, auditable, and cost-efficient by default.

Tags: #databricks #dataengineering #cloud #security

Cover photo by AMONWAT DUMKRUT on Unsplash.

This article was drafted with AI assistance and is intended for technical review and fact-checking before publication.

πŸ“° Read the original article on Dev.to Security

Originally published by Dev.to Security. Aggregated on AIWithGhost for educational purposes β€” full credit and traffic to the original publisher.