Skip to main content

Overview

The Image Analysis API provides two endpoints for working with images:
  1. Upload: Upload images to a temporary CDN (ImgBB)
  2. Analyze: Extract EXIF metadata from uploaded images
Images are uploaded to ImgBB with a configurable expiration time (default: 10 minutes). Ensure you analyze images before they expire.

Upload Image

Upload an image file to temporary storage and receive a URL for analysis.

Endpoint

POST /api/image/upload

Request

Headers

Content-Type: multipart/form-data

Body Parameters

image
File
required
Image file to upload. Supports common formats: JPEG, PNG, GIF, BMP, TIFF.Max size: 32MB (configurable via MAX_IMAGE_SIZE env variable)Example: File from input field or blob

Request Example

curl -X POST http://localhost:3000/api/image/upload \
  -F "image=@/path/to/photo.jpg"

Response

success
boolean
Always true on successful upload
url
string
Direct URL to the uploaded image (suitable for analysis)
displayUrl
string
Alternative display URL (may be different for some CDN configurations)
deleteUrl
string
URL to delete the image before expiration
expiration
number
Time in seconds until the image expires (default: 600)

Success Response

{
  "success": true,
  "url": "https://i.ibb.co/abc123/image.jpg",
  "displayUrl": "https://ibb.co/xyz789",
  "deleteUrl": "https://ibb.co/abc123/delete_token",
  "expiration": 600
}

Error Responses

400
No image file
{
  "error": "No image file provided"
}
400
File too large
{
  "error": "File too large. Maximum size is 32000KB"
}
500
API key not configured
{
  "error": "ImgBB API key not configured"
}
500
Upload failed
{
  "error": "Upload failed"
}

Analyze Image

Extract EXIF metadata from an image URL.

Endpoint

POST /api/image/analyze

Request

Headers

Content-Type: application/json

Body Parameters

imageUrl
string
required
URL of the image to analyze. Must be a valid, accessible URL.Typically the url returned from the upload endpoint.Example: "https://i.ibb.co/abc123/image.jpg"

Request Example

curl -X POST http://localhost:3000/api/image/analyze \
  -H "Content-Type: application/json" \
  -d '{
    "imageUrl": "https://i.ibb.co/abc123/image.jpg"
  }'

Response

success
boolean
Indicates if analysis was successful
imageUrl
string
The URL of the analyzed image
metadata
ImageMetadata
Extracted EXIF metadata from the image

Success Response

{
  "success": true,
  "imageUrl": "https://i.ibb.co/abc123/image.jpg",
  "metadata": {
    "width": 4032,
    "height": 3024,
    "dateTaken": "2024-01-15T14:30:00Z",
    "dateModified": "2024-01-15T14:30:05Z",
    "camera": {
      "make": "Apple",
      "model": "iPhone 13 Pro",
      "software": "16.3"
    },
    "exposure": {
      "aperture": "f/1.5",
      "shutterSpeed": "1/120s",
      "iso": 100,
      "focalLength": "5.7mm",
      "flash": "Not fired"
    },
    "gps": {
      "latitude": 37.7749,
      "longitude": -122.4194,
      "altitude": 16.2
    },
    "orientation": 1,
    "colorSpace": "sRGB"
  }
}

No Metadata Response

If the image has no EXIF data:
{
  "success": true,
  "imageUrl": "https://i.ibb.co/abc123/image.jpg",
  "metadata": {}
}

Error Responses

400
Invalid image URL
{
  "error": "Invalid image URL"
}
400
Invalid URL format
{
  "error": "Invalid URL format"
}
500
Analysis failed
{
  "success": false,
  "error": "Failed to analyze image"
}

Configuration

Set these environment variables for image upload:
# Required: ImgBB API key
IMGBB_API_KEY=your_imgbb_api_key

# Optional: Max file size in KB (default: 32000)
MAX_IMAGE_SIZE=32000

# Optional: Image expiration in seconds (default: 600)
IMAGE_EXPIRY=600
Get a free ImgBB API key at https://api.imgbb.com/

Source Code Reference

  • Upload Route: source/app/api/image/upload/route.ts:9
  • Analyze Route: source/app/api/image/analyze/route.ts:7
  • Metadata Extraction: source/lib/image/metadata.ts:8
  • Type Definitions: source/lib/image/types.ts

Best Practices

Privacy: EXIF data can contain sensitive information like GPS coordinates. Handle with care and inform users.

Recommendations

  1. Strip metadata: Consider offering an option to remove EXIF data
  2. Validate URLs: Ensure image URLs are from trusted sources
  3. Handle missing data: Not all images contain EXIF metadata
  4. GPS accuracy: GPS coordinates may not be exact
  5. Expiration handling: Download or cache analysis results before expiration

Complete Workflow Example

interface ImageMetadata {
  width?: number;
  height?: number;
  dateTaken?: string;
  camera?: {
    make?: string;
    model?: string;
  };
  gps?: {
    latitude: number;
    longitude: number;
    altitude?: number;
  };
}

async function analyzeImage(file: File): Promise<ImageMetadata> {
  // Step 1: Upload the image
  const formData = new FormData();
  formData.append('image', file);
  
  const uploadResponse = await fetch('/api/image/upload', {
    method: 'POST',
    body: formData
  });
  
  const { url } = await uploadResponse.json();
  
  // Step 2: Analyze the uploaded image
  const analyzeResponse = await fetch('/api/image/analyze', {
    method: 'POST',
    headers: { 'Content-Type': 'application/json' },
    body: JSON.stringify({ imageUrl: url })
  });
  
  const { metadata } = await analyzeResponse.json();
  
  return metadata;
}

// Usage
const fileInput = document.querySelector('input[type="file"]');
const metadata = await analyzeImage(fileInput.files[0]);

if (metadata.gps) {
  console.log(`Location: ${metadata.gps.latitude}, ${metadata.gps.longitude}`);
}

if (metadata.camera) {
  console.log(`Camera: ${metadata.camera.make} ${metadata.camera.model}`);
}

Build docs developers (and LLMs) love