Supabase Storage Image Uploader Guide (Agentic Oriented)

Supabase Storage Image Uploader Guide (cURL-Based Approach)



This guide provides comprehensive instructions for working with Supabase Storage using cURL commands. This approach allows an agent to perform all operations directly through the command line.

1. Authentication

All Supabase API requests require authentication. You'll need your Supabase project URL and API key:

# Set environment variables for easier reuse
export SUPABASE_URL="https://YOUR_PROJECT_REF.supabase.co"
export SUPABASE_KEY="YOUR_SUPABASE_KEY"  # Use anon key for client operations or service_role key for admin operations

2. Creating and Managing Buckets

Create a Storage Bucket:

curl -X POST "${SUPABASE_URL}/storage/v1/bucket" \
  -H "Authorization: Bearer ${SUPABASE_KEY}" \
  -H "Content-Type: application/json" \
  -d '{"name": "images", "public": false}'

List All Buckets:

curl -X GET "${SUPABASE_URL}/storage/v1/bucket" \
  -H "Authorization: Bearer ${SUPABASE_KEY}"

Get Bucket Details:

curl -X GET "${SUPABASE_URL}/storage/v1/bucket/images" \
  -H "Authorization: Bearer ${SUPABASE_KEY}"

Update Bucket (Change Public/Private Setting):

curl -X PUT "${SUPABASE_URL}/storage/v1/bucket/images" \
  -H "Authorization: Bearer ${SUPABASE_KEY}" \
  -H "Content-Type: application/json" \
  -d '{"public": true}'

Empty a Bucket:

curl -X POST "${SUPABASE_URL}/storage/v1/bucket/images/empty" \
  -H "Authorization: Bearer ${SUPABASE_KEY}"

Delete a Bucket:

curl -X DELETE "${SUPABASE_URL}/storage/v1/bucket/images" \
  -H "Authorization: Bearer ${SUPABASE_KEY}"

3. Configuring Storage Policies via SQL

Storage policies must be set up through SQL. You can execute SQL through cURL using the Supabase REST API:

Create a Policy to Allow Public Access:

curl -X POST "${SUPABASE_URL}/rest/v1/rpc/execute_sql" \
  -H "Authorization: Bearer ${SUPABASE_KEY}" \
  -H "Content-Type: application/json" \
  -d '{
    "query": "CREATE POLICY \"Allow public access\" ON storage.objects FOR SELECT USING (bucket_id = '\''images'\'');"
  }'

Create a Policy to Allow Authenticated Uploads:

curl -X POST "${SUPABASE_URL}/rest/v1/rpc/execute_sql" \
  -H "Authorization: Bearer ${SUPABASE_KEY}" \
  -H "Content-Type: application/json" \
  -d '{
    "query": "CREATE POLICY \"Allow authenticated uploads\" ON storage.objects FOR INSERT TO authenticated WITH CHECK (bucket_id = '\''images'\'');"
  }'

Create a Policy to Allow Anonymous Uploads:

curl -X POST "${SUPABASE_URL}/rest/v1/rpc/execute_sql" \
  -H "Authorization: Bearer ${SUPABASE_KEY}" \
  -H "Content-Type: application/json" \
  -d '{
    "query": "CREATE POLICY \"Allow anonymous uploads\" ON storage.objects FOR INSERT USING (bucket_id = '\''images'\'');"
  }'

4. File Operations

Upload a File:

curl -X POST "${SUPABASE_URL}/storage/v1/object/images/path/to/image.jpg" \
  -H "Authorization: Bearer ${SUPABASE_KEY}" \
  -H "Content-Type: image/jpeg" \
  --data-binary "@/local/path/to/image.jpg"

List Files in a Bucket:

curl -X GET "${SUPABASE_URL}/storage/v1/object/list/images" \
  -H "Authorization: Bearer ${SUPABASE_KEY}"

List Files in a Folder:

curl -X GET "${SUPABASE_URL}/storage/v1/object/list/images?prefix=folder/" \
  -H "Authorization: Bearer ${SUPABASE_KEY}"

Download a File:

curl -X GET "${SUPABASE_URL}/storage/v1/object/images/path/to/image.jpg" \
  -H "Authorization: Bearer ${SUPABASE_KEY}" \
  --output downloaded_image.jpg

Get Public URL (For Public Buckets):

curl -X GET "${SUPABASE_URL}/storage/v1/object/public/images/path/to/image.jpg" \
  -H "Authorization: Bearer ${SUPABASE_KEY}"

Create a Signed URL (For Private Buckets):

curl -X POST "${SUPABASE_URL}/storage/v1/object/sign/images/path/to/image.jpg" \
  -H "Authorization: Bearer ${SUPABASE_KEY}" \
  -H "Content-Type: application/json" \
  -d '{"expiresIn": 3600}'

Move/Rename a File:

curl -X POST "${SUPABASE_URL}/storage/v1/object/move" \
  -H "Authorization: Bearer ${SUPABASE_KEY}" \
  -H "Content-Type: application/json" \
  -d '{
    "bucketId": "images",
    "sourceKey": "original/path/image.jpg",
    "destinationKey": "new/path/renamed-image.jpg"
  }'

Copy a File:

curl -X POST "${SUPABASE_URL}/storage/v1/object/copy" \
  -H "Authorization: Bearer ${SUPABASE_KEY}" \
  -H "Content-Type: application/json" \
  -d '{
    "bucketId": "images", 
    "sourceKey": "path/to/source.jpg",
    "destinationKey": "path/to/destination.jpg"
  }'

Delete a File:

curl -X DELETE "${SUPABASE_URL}/storage/v1/object/images/path/to/image.jpg" \
  -H "Authorization: Bearer ${SUPABASE_KEY}"

Delete Multiple Files:

curl -X DELETE "${SUPABASE_URL}/storage/v1/object/images" \
  -H "Authorization: Bearer ${SUPABASE_KEY}" \
  -H "Content-Type: application/json" \
  -d '{
    "prefixes": ["file1.jpg", "folder/file2.jpg"]
  }'

5. Complete Image Upload Example Script

Below is a complete shell script that:

  1. Creates a bucket
  2. Sets appropriate policies
  3. Uploads an image
  4. Gets the public URL
#!/bin/bash

# Configuration
SUPABASE_URL="https://YOUR_PROJECT_REF.supabase.co"
SUPABASE_KEY="YOUR_SUPABASE_KEY"
BUCKET_NAME="images"
LOCAL_IMAGE_PATH="/path/to/your/image.jpg"
REMOTE_IMAGE_PATH="uploads/image.jpg"

# 1. Create a bucket
echo "Creating bucket..."
curl -X POST "${SUPABASE_URL}/storage/v1/bucket" \
  -H "Authorization: Bearer ${SUPABASE_KEY}" \
  -H "Content-Type: application/json" \
  -d "{\"name\": \"${BUCKET_NAME}\", \"public\": true}"

# 2. Create policy for public access (make files readable)
echo "Creating policy for public access..."
curl -X POST "${SUPABASE_URL}/rest/v1/rpc/execute_sql" \
  -H "Authorization: Bearer ${SUPABASE_KEY}" \
  -H "Content-Type: application/json" \
  -d "{
    \"query\": \"CREATE POLICY \\\"Allow public access\\\" ON storage.objects FOR SELECT USING (bucket_id = '${BUCKET_NAME}');\"
  }"

# 3. Create policy for uploads
echo "Creating policy for uploads..."
curl -X POST "${SUPABASE_URL}/rest/v1/rpc/execute_sql" \
  -H "Authorization: Bearer ${SUPABASE_KEY}" \
  -H "Content-Type: application/json" \
  -d "{
    \"query\": \"CREATE POLICY \\\"Allow uploads\\\" ON storage.objects FOR INSERT USING (bucket_id = '${BUCKET_NAME}');\"
  }"

# 4. Upload an image
echo "Uploading image..."
curl -X POST "${SUPABASE_URL}/storage/v1/object/${BUCKET_NAME}/${REMOTE_IMAGE_PATH}" \
  -H "Authorization: Bearer ${SUPABASE_KEY}" \
  -H "Content-Type: image/jpeg" \
  --data-binary "@${LOCAL_IMAGE_PATH}"

# 5. Get the public URL
echo "Image uploaded successfully!"
echo "Public URL: ${SUPABASE_URL}/storage/v1/object/public/${BUCKET_NAME}/${REMOTE_IMAGE_PATH}"

6. Important Security Considerations

  1. API Key Security:

    • The service_role key has admin privileges - use it cautiously and never expose it publicly
    • The anon key can be used for client operations with appropriate RLS policies
  2. Row Level Security (RLS):

    • Always set up appropriate RLS policies to control access to your files
    • Test your policies thoroughly to ensure they provide the expected security
  3. File Size Limits:

    • Standard uploads work best for files under 6MB
    • For larger files (up to 5GB), consider splitting them or using the TUS protocol (not available via simple cURL)
  4. Public vs. Private Buckets:

    • Public buckets allow anyone with the URL to access files
    • Private buckets require authentication or signed URLs to access files

For more detailed information and advanced use cases, refer to the official Supabase Storage documentation.

Comments

Popular posts from this blog

local LLM runners like Ollama, GPT4All, and LMStudio

Understanding Radix UI, shadcn/ui, and Component Architecture in Modern Web Development