DEV Community

Python-T Point
Python-T Point

Posted on • Originally published at pythontpoint.in

๐Ÿ Mastering OCI bucket policies with Python SDK

๐Ÿ’ก Setup โ€” Why Preparation Matters

OCI bucket policies with Python SDK

A proper environment eliminates runtime surprises when working with OCI bucket policies via the Python SDK; the workflow depends on an authenticated client object.

๐Ÿ“‘ Table of Contents

  • ๐Ÿ’ก Setup โ€” Why Preparation Matters
  • ๐Ÿ” Policy Structure โ€” How OCI Interprets Policies
  • ๐Ÿ— Statement Anatomy โ€” What Each Field Does
  • ๐Ÿ›  Building the Policy with Python SDK
  • ๐Ÿ›  Creating a Policy โ€” Applying It to a Bucket
  • ๐Ÿ”„ Updating and Deleting โ€” Managing Policy Lifecycle
  • โœ๏ธ Update Example โ€” Adding a Write Permission
  • ๐Ÿ—‘ Delete Example โ€” Removing All Custom Rules
  • ๐Ÿ“Š Testing and Validation โ€” Verifying OCI Bucket Policies with Python SDK
  • ๐ŸŸฉ Final Thoughts
  • โ“ Frequently Asked Questions
  • How do I list the current policy of a bucket?
  • Can I apply multiple policies to the same bucket?
  • What is the limit on policy size?
  • ๐Ÿ“š References & Further Reading

๐Ÿ” Policy Structure โ€” How OCI Interprets Policies

OCI bucket policy is a JSON document evaluated for each request; the SDK serializes this structure into a string passed to the put_bucket_policy API.

A policy consists of an array of statements, each defining an effect, a list of actions, a principal, and a condition that limits when the statement applies.

OCI bucket policy is a set of JSON statements that grant or deny permissions on a bucket based on request attributes.

According to the official OCI documentation, the policy language supports wildcards and condition operators that are evaluated serverโ€‘side, reducing network chatter.

๐Ÿ— Statement Anatomy โ€” What Each Field Does

{ "Version": "20190401", "Statement": [ { "Effect": "Allow", "Action": ["OBJECT_READ"], "Principal": {"AWS": ["*"]}, "Resource": ["arn:oci:objectstorage:us-phoenix-1:example-tenancy:bucket/example-bucket/*"] } ]
}
Enter fullscreen mode Exit fullscreen mode

What this does:

  • Version: Schema version; required for forward compatibility.
  • Effect: Either Allow or Deny.
  • Action: List of OCI Object Storage actions (e.g., OBJECT_READ).
  • Principal: Who the statement applies to; * means any authenticated principal.
  • Resource: ARN pattern matching objects inside the bucket.

๐Ÿ›  Building the Policy with Python SDK

# build_policy.py
import json policy = { "Version": "20190401", "Statement": [ { "Effect": "Allow", "Action": ["OBJECT_READ"], "Principal": {"AWS": ["*"]}, "Resource": [f"arn:oci:objectstorage:{config['region']}:{config['tenancy']}:bucket/{bucket_name}/*"] } ]
} policy_json = json.dumps(policy, indent=2)
print(policy_json)
Enter fullscreen mode Exit fullscreen mode

Serializing with json.dumps guarantees proper quoting and ordering, which the SDK transmits unchanged.

Key point: The policy JSON must be valid UTFโ€‘8; malformed syntax triggers a 400 Bad Request before any evaluation occurs. (More onPythonTPoint tutorials)


๐Ÿ›  Creating a Policy โ€” Applying It to a Bucket

Creating a policy attaches the JSON document to a bucket, making the access rules enforceable immediately. (Also read: โ˜๏ธ OCI vs GCP compute pricing for Docker โ€” which one should you use?)

# apply_policy.py
import oci
import json config = oci.config.from_file()
client = oci.object_storage.ObjectStorageClient(config) bucket_name = "example-bucket"
policy_path = "policy.json" # Load JSON from file
with open(policy_path, "r") as f: policy_json = f.read() response = client.put_bucket_policy( namespace_name=client.get_namespace().data, bucket_name=bucket_name, put_bucket_policy_details=oci.object_storage.models.PutBucketPolicyDetails( policy=policy_json )
) print(f"Status: {response.status}")
Enter fullscreen mode Exit fullscreen mode

What this does:

  • client.get_namespace(): Retrieves the tenancy namespace required for all Object Storage calls.
  • put_bucket_policy: Sends a PUT request with the policy string.
  • response.status: HTTP status; 200 indicates success.

    $ python apply_policy.py
    Status: 200

The SDK call is reproducible, versionโ€‘controlled, and CIโ€‘compatible, unlike a oneโ€‘off console edit.

Consistent policy deployment through code eliminates drift between environments.

Key point: Once attached, the policy is evaluated for every request, providing a single source of truth for bucket permissions. (Also read: โ˜๏ธ S3 bucket policy vs ACL comparison โ€” which one should you use?)


๐Ÿ”„ Updating and Deleting โ€” Managing Policy Lifecycle

Updating a policy replaces the existing JSON document; deleting removes all custom rules, reverting to the default implicit deny.

โœ๏ธ Update Example โ€” Adding a Write Permission

# update_policy.py
import oci, json config = oci.config.from_file()
client = oci.object_storage.ObjectStorageClient(config) bucket_name = "example-bucket" # Retrieve current policy
current = client.get_bucket_policy( namespace_name=client.get_namespace().data, bucket_name=bucket_name
).data.policy policy = json.loads(current)
policy["Statement"].append({ "Effect": "Allow", "Action": ["OBJECT_WRITE"], "Principal": {"AWS": ["*"]}, "Resource": [f"arn:oci:objectstorage:{config['region']}:{config['tenancy']}:bucket/{bucket_name}/*"]
}) updated_json = json.dumps(policy, indent=2) client.put_bucket_policy( namespace_name=client.get_namespace().data, bucket_name=bucket_name, put_bucket_policy_details=oci.object_storage.models.PutBucketPolicyDetails( policy=updated_json )
) print("Policy updated")



$ python update_policy.py
Policy updated
Enter fullscreen mode Exit fullscreen mode

๐Ÿ—‘ Delete Example โ€” Removing All Custom Rules

# delete_policy.py
import oci config = oci.config.from_file()
client = oci.object_storage.ObjectStorageClient(config) bucket_name = "example-bucket" client.delete_bucket_policy( namespace_name=client.get_namespace().data, bucket_name=bucket_name
) print("Policy deleted")



$ python delete_policy.py
Policy deleted
Enter fullscreen mode Exit fullscreen mode

Deleting first guarantees that stale statements are not retained if the new policy accidentally omits required fields.

Key point: The SDK raises oci.exceptions.ServiceError on failure, enabling programmatic retries.


๐Ÿ“Š Testing and Validation โ€” Verifying OCI Bucket Policies with Python SDK

Testing confirms that the policy behaves as intended before it reaches production workloads.

Use a temporary object and attempt operations that should be allowed or denied based on the current policy.

# test_policy.py
import oci, json, uuid config = oci.config.from_file()
client = oci.object_storage.ObjectStorageClient(config) ns = client.get_namespace().data
bucket = "example-bucket"
obj_name = f"test-{uuid.uuid4()}.txt"
content = b"policy test" # Upload object โ€“ should succeed if OBJECT_WRITE is allowed
try: client.put_object( namespace_name=ns, bucket_name=bucket, object_name=obj_name, put_object_body=content ) print("Upload succeeded")
except oci.exceptions.ServiceError as e: print(f"Upload failed: {e.message}") # Attempt to delete โ€“ should fail if only READ is allowed
try: client.delete_object( namespace_name=ns, bucket_name=bucket, object_name=obj_name ) print("Delete succeeded")
except oci.exceptions.ServiceError as e: print(f"Delete failed: {e.message}")



$ python test_policy.py
Upload succeeded
Delete failed: Forbidden
Enter fullscreen mode Exit fullscreen mode

The SDK surfaces HTTP 403 as a ServiceError, making it straightforward to assert expected outcomes in unit tests.

Key point: Automated tests catch policy regressions early, preventing accidental privilege escalation.


๐ŸŸฉ Final Thoughts

OCI bucket policies with the Python SDK provide a programmatic, repeatable method for enforcing fineโ€‘grained access controls. Constructing the JSON policy in code keeps the definition versioned alongside application logic, reducing drift between environments.

Understanding the evaluation mechanismโ€”how the service parses each statement and matches it against request attributesโ€”enables the design of policies that are both secure and performant. The SDKโ€™s builtโ€‘in error handling and pagination simplify integration into CI pipelines, making policy management a firstโ€‘class part of the deployment workflow.

โ“ Frequently Asked Questions

How do I list the current policy of a bucket?

Use client.get_bucket_policy with the namespace and bucket name; the response contains the policy JSON string.

Can I apply multiple policies to the same bucket?

No. OCI allows only a single policy document per bucket; combine all statements into one JSON document.

What is the limit on policy size?

OCI enforces a maximum of 20 KB for the policy string; exceeding this limit returns a 413 Payload Too Large error.

๐Ÿ’ก Want to practise this hands-on? DigitalOcean gives new accounts $200 free credit for 60 days โ€” enough to spin up a full Linux/Docker/Kubernetes environment at no cost.

๐Ÿ“š Recommended reading: Best DevOps & cloud books on Amazon โ€” from Linux fundamentals to Kubernetes in production, curated for working engineers.

๐Ÿ“š References & Further Reading

  • Python JSON handling โ€” best practices for serializing policy documents: docs.python.org

Top comments (0)