{
  "openapi": "3.1.0",
  "info": {
    "title": "FlashShot Developer API",
    "version": "1.0.0",
    "description": "Production-grade RESTful API for AI-powered studio product photography and relighting.",
    "contact": {
      "name": "FlashShot Developer Support",
      "url": "https://flashshot.io/docs",
      "email": "support@flashshot.io"
    }
  },
  "servers": [
    {
      "url": "https://api.flashshot.io/v1",
      "description": "Production Server"
    }
  ],
  "security": [
    {
      "BearerAuth": []
    },
    {
      "ApiKeyAuth": []
    }
  ],
  "paths": {
    "/transform": {
      "post": {
        "summary": "AI Studio Relighting",
        "description": "Transforms a raw product image into a high-resolution studio photo using specified lighting themes. Atomically deducts 1 credit.",
        "operationId": "transformImage",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/TransformRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Transformation successful",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/TransformResponse"
                }
              }
            }
          },
          "400": {
            "description": "Invalid input or missing fields",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized (missing, invalid, or revoked API key)",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "402": {
            "description": "Payment Required (insufficient credit balance)",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "413": {
            "description": "Payload too large (>4.5MB)",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "502": {
            "description": "AI model cascade failure (credits preserved)",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        }
      }
    },
    "/refine": {
      "post": {
        "summary": "Iterative Prompt-Based Refinement",
        "description": "Refines a previous studio render with natural language lighting/shadow adjustments without altering product geometry. Atomically deducts 1 credit.",
        "operationId": "refineImage",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/RefineRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Refinement successful",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/RefineResponse"
                }
              }
            }
          },
          "400": {
            "description": "Missing parameters or invalid parent job",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "402": {
            "description": "Insufficient credits",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "404": {
            "description": "Parent job not found or unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        }
      }
    },
    "/jobs/{id}": {
      "get": {
        "summary": "Get Job Details",
        "description": "Retrieves status, output URLs, and timestamps of a specific job.",
        "operationId": "getJob",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Unique job identifier",
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Job found",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/JobResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          },
          "404": {
            "description": "Job not found"
          }
        }
      }
    },
    "/themes": {
      "get": {
        "summary": "List Active Themes & Formats",
        "description": "Returns all active lighting presets, reference images, and supported aspect ratios.",
        "operationId": "listThemes",
        "security": [],
        "responses": {
          "200": {
            "description": "List of themes and formats",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ThemesResponse"
                }
              }
            }
          }
        }
      }
    },
    "/account": {
      "get": {
        "summary": "Get Account Details & Credits",
        "description": "Returns authenticated user details, credit balance, subscription tier, and API rate limits.",
        "operationId": "getAccount",
        "responses": {
          "200": {
            "description": "Account details retrieved",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AccountResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized"
          }
        }
      }
    },
    "/openapi.json": {
      "get": {
        "summary": "OpenAPI Specification",
        "description": "Returns the OpenAPI 3.1.0 JSON specification for FlashShot Developer API.",
        "operationId": "getOpenApiSpec",
        "security": [],
        "responses": {
          "200": {
            "description": "OpenAPI specification JSON",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          }
        }
      }
    }
  },
  "components": {
    "securitySchemes": {
      "BearerAuth": {
        "type": "http",
        "scheme": "bearer",
        "bearerFormat": "API Key",
        "description": "Provide your API key formatted as `Authorization: Bearer fs_live_...`"
      },
      "ApiKeyAuth": {
        "type": "apiKey",
        "in": "header",
        "name": "x-api-key",
        "description": "Provide your API key in the `x-api-key` header"
      }
    },
    "schemas": {
      "TransformRequest": {
        "type": "object",
        "required": [
          "image",
          "theme_key"
        ],
        "properties": {
          "image": {
            "type": "string",
            "description": "Base64 data URI (data:image/png;base64,...), raw Base64 string, or public image URL (https://...)"
          },
          "theme_key": {
            "type": "string",
            "description": "Theme preset key (e.g. clean_studio, marble, wood, podium)"
          },
          "format_key": {
            "type": "string",
            "default": "square",
            "description": "Aspect ratio format (square, portrait, landscape, story)"
          },
          "original_filename": {
            "type": "string",
            "default": "image.png",
            "description": "Optional original filename for semantic CDN URLs"
          }
        }
      },
      "TransformResponse": {
        "type": "object",
        "properties": {
          "success": {
            "type": "boolean"
          },
          "job_id": {
            "type": "string"
          },
          "jobId": {
            "type": "string"
          },
          "output_url": {
            "type": "string"
          },
          "credits_remaining": {
            "type": "integer"
          },
          "theme_used": {
            "type": "string"
          },
          "format_used": {
            "type": "string"
          },
          "created_at": {
            "type": "integer"
          }
        }
      },
      "RefineRequest": {
        "type": "object",
        "required": [
          "parent_job_id",
          "custom_prompt"
        ],
        "properties": {
          "parent_job_id": {
            "type": "string",
            "description": "Job ID of the original transform or prior refine render"
          },
          "custom_prompt": {
            "type": "string",
            "description": "Natural language instructions for lighting, reflections, or shadow adjustments"
          }
        }
      },
      "RefineResponse": {
        "type": "object",
        "properties": {
          "success": {
            "type": "boolean"
          },
          "job_id": {
            "type": "string"
          },
          "jobId": {
            "type": "string"
          },
          "parent_job_id": {
            "type": "string"
          },
          "output_url": {
            "type": "string"
          },
          "credits_remaining": {
            "type": "integer"
          },
          "created_at": {
            "type": "integer"
          }
        }
      },
      "JobResponse": {
        "type": "object",
        "properties": {
          "success": {
            "type": "boolean"
          },
          "job": {
            "type": "object",
            "properties": {
              "id": {
                "type": "string"
              },
              "status": {
                "type": "string"
              },
              "theme_used": {
                "type": "string"
              },
              "format_used": {
                "type": "string"
              },
              "output_url": {
                "type": "string",
                "nullable": true
              },
              "is_hd": {
                "type": "integer"
              },
              "created_at": {
                "type": "integer"
              },
              "parent_job_id": {
                "type": "string",
                "nullable": true
              }
            }
          }
        }
      },
      "ThemesResponse": {
        "type": "object",
        "properties": {
          "success": {
            "type": "boolean"
          },
          "themes": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "key": {
                  "type": "string"
                },
                "name": {
                  "type": "string"
                },
                "color": {
                  "type": "string"
                },
                "preview_url": {
                  "type": "string",
                  "nullable": true
                }
              }
            }
          },
          "formats": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "key": {
                  "type": "string"
                },
                "label": {
                  "type": "string"
                }
              }
            }
          }
        }
      },
      "AccountResponse": {
        "type": "object",
        "properties": {
          "success": {
            "type": "boolean"
          },
          "account": {
            "type": "object",
            "properties": {
              "user_id": {
                "type": "string"
              },
              "email": {
                "type": "string"
              },
              "tier": {
                "type": "string"
              },
              "subscription_tier": {
                "type": "string"
              },
              "credits": {
                "type": "integer"
              },
              "credit_details": {
                "type": "object",
                "properties": {
                  "balance": {
                    "type": "integer"
                  },
                  "total_used": {
                    "type": "integer"
                  }
                }
              },
              "rate_limits": {
                "type": "object",
                "properties": {
                  "requests_per_minute": {
                    "type": "integer"
                  },
                  "max_concurrent_jobs": {
                    "type": "integer"
                  }
                }
              },
              "created_at": {
                "type": "integer"
              }
            }
          }
        }
      },
      "ErrorResponse": {
        "type": "object",
        "properties": {
          "error": {
            "type": "string"
          },
          "status": {
            "type": "integer"
          },
          "code": {
            "type": "string"
          },
          "credits_remaining": {
            "type": "integer"
          }
        }
      }
    }
  }
}