{
  "openapi": "3.1.0",
  "info": {
    "title": "Local Photo Watermark Discovery API",
    "version": "1.0.0",
    "description": "Read-only public resources. No hosted image processing or upload endpoint. Use the browser SDK or explicitly connected local MCP for execution."
  },
  "servers": [
    {
      "url": "https://watermark.noxxxx.com"
    }
  ],
  "paths": {
    "/api/v1/capabilities.json": {
      "get": {
        "operationId": "_api_v1_capabilities_json",
        "summary": "Read capabilities.json",
        "responses": {
          "200": {
            "description": "Static public JSON; no photo data.",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "version",
                    "name",
                    "language",
                    "availableLanguages",
                    "localizedPages",
                    "documentation",
                    "machineDocumentation",
                    "openapi",
                    "recipeSchema",
                    "browserSdk",
                    "execution",
                    "imageUploadEndpoint",
                    "authentication",
                    "price",
                    "pricing",
                    "input",
                    "output",
                    "limits",
                    "capabilities",
                    "mcp"
                  ],
                  "properties": {
                    "version": {
                      "type": "number"
                    },
                    "name": {
                      "type": "string"
                    },
                    "language": {
                      "type": "string"
                    },
                    "availableLanguages": {
                      "type": "array",
                      "items": {
                        "type": "string"
                      }
                    },
                    "localizedPages": {
                      "type": "array",
                      "items": {
                        "type": "object",
                        "required": [
                          "language",
                          "documentation",
                          "tools"
                        ],
                        "properties": {
                          "language": {
                            "type": "string"
                          },
                          "documentation": {
                            "type": "string"
                          },
                          "tools": {
                            "type": "array",
                            "items": {
                              "type": "string"
                            }
                          }
                        }
                      }
                    },
                    "documentation": {
                      "type": "string"
                    },
                    "machineDocumentation": {
                      "type": "string"
                    },
                    "openapi": {
                      "type": "string"
                    },
                    "recipeSchema": {
                      "type": "string"
                    },
                    "browserSdk": {
                      "type": "string"
                    },
                    "execution": {
                      "type": "string"
                    },
                    "imageUploadEndpoint": {
                      "type": "null"
                    },
                    "authentication": {
                      "type": "string"
                    },
                    "price": {
                      "type": "number"
                    },
                    "pricing": {
                      "type": "object",
                      "required": [
                        "amount",
                        "currency",
                        "paidTiers"
                      ],
                      "properties": {
                        "amount": {
                          "type": "number"
                        },
                        "currency": {
                          "type": "string"
                        },
                        "paidTiers": {
                          "type": "boolean"
                        }
                      }
                    },
                    "input": {
                      "type": "array",
                      "items": {
                        "type": "string"
                      }
                    },
                    "output": {
                      "type": "array",
                      "items": {
                        "type": "string"
                      }
                    },
                    "limits": {
                      "type": "object",
                      "required": [
                        "maxInputBytes",
                        "maxInputPixels",
                        "maxZipBytes",
                        "maxLayers"
                      ],
                      "properties": {
                        "maxInputBytes": {
                          "type": "number"
                        },
                        "maxInputPixels": {
                          "type": "number"
                        },
                        "maxZipBytes": {
                          "type": "number"
                        },
                        "maxLayers": {
                          "type": "number"
                        }
                      }
                    },
                    "capabilities": {
                      "type": "array",
                      "items": {
                        "type": "object",
                        "required": [
                          "id",
                          "name",
                          "page",
                          "description",
                          "recipe",
                          "searchTerms"
                        ],
                        "properties": {
                          "id": {
                            "type": "string"
                          },
                          "name": {
                            "type": "string"
                          },
                          "page": {
                            "type": "string"
                          },
                          "description": {
                            "type": "string"
                          },
                          "recipe": {
                            "type": "string"
                          },
                          "searchTerms": {
                            "type": "array",
                            "items": {
                              "type": "string"
                            }
                          }
                        }
                      }
                    },
                    "mcp": {
                      "type": "object",
                      "required": [
                        "transport",
                        "hostedEndpoint",
                        "documentation",
                        "tools",
                        "requiresExplicitConnection"
                      ],
                      "properties": {
                        "transport": {
                          "type": "string"
                        },
                        "hostedEndpoint": {
                          "type": "null"
                        },
                        "documentation": {
                          "type": "string"
                        },
                        "tools": {
                          "type": "string"
                        },
                        "requiresExplicitConnection": {
                          "type": "boolean"
                        }
                      }
                    }
                  }
                },
                "example": {
                  "version": 1,
                  "name": "Local Photo Watermark",
                  "language": "en",
                  "availableLanguages": [
                    "zh",
                    "zh-Hant",
                    "en",
                    "ja",
                    "ko",
                    "fr",
                    "de",
                    "es",
                    "pt",
                    "it",
                    "ru",
                    "ar",
                    "hi",
                    "id",
                    "vi",
                    "th",
                    "tr",
                    "nl",
                    "pl",
                    "sv",
                    "uk"
                  ],
                  "localizedPages": [
                    {
                      "language": "zh",
                      "documentation": "/zh/developers/",
                      "tools": [
                        "/zh/batch-watermark-photos/",
                        "/zh/add-filename-to-photo/",
                        "/zh/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "zh-Hant",
                      "documentation": "/zh-Hant/developers/",
                      "tools": [
                        "/zh-Hant/batch-watermark-photos/",
                        "/zh-Hant/add-filename-to-photo/",
                        "/zh-Hant/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "en",
                      "documentation": "/developers/",
                      "tools": [
                        "/batch-watermark-photos/",
                        "/add-filename-to-photo/",
                        "/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "ja",
                      "documentation": "/ja/developers/",
                      "tools": [
                        "/ja/batch-watermark-photos/",
                        "/ja/add-filename-to-photo/",
                        "/ja/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "ko",
                      "documentation": "/ko/developers/",
                      "tools": [
                        "/ko/batch-watermark-photos/",
                        "/ko/add-filename-to-photo/",
                        "/ko/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "fr",
                      "documentation": "/fr/developers/",
                      "tools": [
                        "/fr/batch-watermark-photos/",
                        "/fr/add-filename-to-photo/",
                        "/fr/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "de",
                      "documentation": "/de/developers/",
                      "tools": [
                        "/de/batch-watermark-photos/",
                        "/de/add-filename-to-photo/",
                        "/de/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "es",
                      "documentation": "/es/developers/",
                      "tools": [
                        "/es/batch-watermark-photos/",
                        "/es/add-filename-to-photo/",
                        "/es/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "pt",
                      "documentation": "/pt/developers/",
                      "tools": [
                        "/pt/batch-watermark-photos/",
                        "/pt/add-filename-to-photo/",
                        "/pt/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "it",
                      "documentation": "/it/developers/",
                      "tools": [
                        "/it/batch-watermark-photos/",
                        "/it/add-filename-to-photo/",
                        "/it/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "ru",
                      "documentation": "/ru/developers/",
                      "tools": [
                        "/ru/batch-watermark-photos/",
                        "/ru/add-filename-to-photo/",
                        "/ru/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "ar",
                      "documentation": "/ar/developers/",
                      "tools": [
                        "/ar/batch-watermark-photos/",
                        "/ar/add-filename-to-photo/",
                        "/ar/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "hi",
                      "documentation": "/hi/developers/",
                      "tools": [
                        "/hi/batch-watermark-photos/",
                        "/hi/add-filename-to-photo/",
                        "/hi/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "id",
                      "documentation": "/id/developers/",
                      "tools": [
                        "/id/batch-watermark-photos/",
                        "/id/add-filename-to-photo/",
                        "/id/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "vi",
                      "documentation": "/vi/developers/",
                      "tools": [
                        "/vi/batch-watermark-photos/",
                        "/vi/add-filename-to-photo/",
                        "/vi/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "th",
                      "documentation": "/th/developers/",
                      "tools": [
                        "/th/batch-watermark-photos/",
                        "/th/add-filename-to-photo/",
                        "/th/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "tr",
                      "documentation": "/tr/developers/",
                      "tools": [
                        "/tr/batch-watermark-photos/",
                        "/tr/add-filename-to-photo/",
                        "/tr/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "nl",
                      "documentation": "/nl/developers/",
                      "tools": [
                        "/nl/batch-watermark-photos/",
                        "/nl/add-filename-to-photo/",
                        "/nl/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "pl",
                      "documentation": "/pl/developers/",
                      "tools": [
                        "/pl/batch-watermark-photos/",
                        "/pl/add-filename-to-photo/",
                        "/pl/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "sv",
                      "documentation": "/sv/developers/",
                      "tools": [
                        "/sv/batch-watermark-photos/",
                        "/sv/add-filename-to-photo/",
                        "/sv/add-date-stamp-to-photos/"
                      ]
                    },
                    {
                      "language": "uk",
                      "documentation": "/uk/developers/",
                      "tools": [
                        "/uk/batch-watermark-photos/",
                        "/uk/add-filename-to-photo/",
                        "/uk/add-date-stamp-to-photos/"
                      ]
                    }
                  ],
                  "documentation": "/developers/",
                  "machineDocumentation": "/developers/api.md",
                  "openapi": "/openapi.json",
                  "recipeSchema": "/api/v1/recipe.schema.json",
                  "browserSdk": "/sdk/watermark.js",
                  "execution": "browser-local",
                  "imageUploadEndpoint": null,
                  "authentication": "none",
                  "price": 0,
                  "pricing": {
                    "amount": 0,
                    "currency": "USD",
                    "paidTiers": false
                  },
                  "input": [
                    "JPEG",
                    "PNG",
                    "WebP",
                    "HEIC/HEIF (first decoded image)"
                  ],
                  "output": [
                    "JPEG",
                    "PNG",
                    "WebP",
                    "ZIP"
                  ],
                  "limits": {
                    "maxInputBytes": 157286400,
                    "maxInputPixels": 120000000,
                    "maxZipBytes": 471859200,
                    "maxLayers": 30
                  },
                  "capabilities": [
                    {
                      "id": "batch-watermark",
                      "name": "Batch watermark",
                      "page": "/batch-watermark-photos/",
                      "description": "To watermark multiple photos for free, select your images below, enter your text or add a logo, preview the placement, and download the batch as a ZIP. Processing runs in your browser; the exported images contain only the marks you choose.",
                      "recipe": "/api/v1/recipes/watermark.json",
                      "searchTerms": [
                        "batch watermark photos",
                        "bulk watermark images",
                        "watermark multiple photos",
                        "add logo to multiple photos",
                        "free batch watermark"
                      ]
                    },
                    {
                      "id": "filename-label",
                      "name": "Filename labels",
                      "page": "/add-filename-to-photo/",
                      "description": "To print filenames on photos, select your images below. The filename preset reads each file’s name and draws it in a footer. Use {filename} without the extension, {fullname} with it, or {index} for a sequence number. This labels image pixels; it does not rename the source files.",
                      "recipe": "/api/v1/recipes/filename.json",
                      "searchTerms": [
                        "add filename to photo",
                        "filename watermark",
                        "print filename on photos",
                        "batch add filenames to images",
                        "overlay filename on image"
                      ]
                    },
                    {
                      "id": "date-stamp",
                      "name": "Date stamp",
                      "page": "/add-date-stamp-to-photos/",
                      "description": "To add the original date taken to multiple photos, select the images below and keep EXIF capture date as the date source. The tool reads each photo’s own date. If it is missing, choose a custom date or a missing-date rule; file modification time is never substituted for capture time.",
                      "recipe": "/api/v1/recipes/date.json",
                      "searchTerms": [
                        "add date stamp to photos",
                        "batch date stamp photos",
                        "add timestamp to photo",
                        "photo date stamper",
                        "EXIF date stamp"
                      ]
                    }
                  ],
                  "mcp": {
                    "transport": "stdio",
                    "hostedEndpoint": null,
                    "documentation": "/developers/api.md#local-mcp",
                    "tools": "/api/v1/mcp-tools.json",
                    "requiresExplicitConnection": true
                  }
                }
              }
            }
          }
        }
      }
    },
    "/api/v1/templates.json": {
      "get": {
        "operationId": "_api_v1_templates_json",
        "summary": "Read templates.json",
        "responses": {
          "200": {
            "description": "Static public JSON; no photo data.",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "version",
                    "schema",
                    "templates",
                    "variables"
                  ],
                  "properties": {
                    "version": {
                      "type": "number"
                    },
                    "schema": {
                      "type": "string"
                    },
                    "templates": {
                      "type": "array",
                      "items": {
                        "type": "object",
                        "required": [
                          "id",
                          "recipeUrl",
                          "recipe"
                        ],
                        "properties": {
                          "id": {
                            "type": "string"
                          },
                          "recipeUrl": {
                            "type": "string"
                          },
                          "recipe": {
                            "type": "object",
                            "required": [
                              "version",
                              "layers",
                              "image",
                              "date",
                              "sequence",
                              "frame",
                              "output"
                            ],
                            "properties": {
                              "version": {
                                "type": "number"
                              },
                              "layers": {
                                "type": "array",
                                "items": {
                                  "type": "object",
                                  "required": [
                                    "id",
                                    "type",
                                    "text",
                                    "assetId",
                                    "fontFamily",
                                    "weight",
                                    "size",
                                    "color",
                                    "opacity",
                                    "angle",
                                    "position",
                                    "x",
                                    "y",
                                    "margin",
                                    "tiled",
                                    "gap",
                                    "stroke",
                                    "shadow",
                                    "autoContrast"
                                  ],
                                  "properties": {
                                    "id": {
                                      "type": "string"
                                    },
                                    "type": {
                                      "type": "string"
                                    },
                                    "text": {
                                      "type": "string"
                                    },
                                    "assetId": {
                                      "type": "string"
                                    },
                                    "fontFamily": {
                                      "type": "string"
                                    },
                                    "weight": {
                                      "type": "string"
                                    },
                                    "size": {
                                      "type": "number"
                                    },
                                    "color": {
                                      "type": "string"
                                    },
                                    "opacity": {
                                      "type": "number"
                                    },
                                    "angle": {
                                      "type": "number"
                                    },
                                    "position": {
                                      "type": "string"
                                    },
                                    "x": {
                                      "type": "number"
                                    },
                                    "y": {
                                      "type": "number"
                                    },
                                    "margin": {
                                      "type": "number"
                                    },
                                    "tiled": {
                                      "type": "boolean"
                                    },
                                    "gap": {
                                      "type": "number"
                                    },
                                    "stroke": {
                                      "type": "boolean"
                                    },
                                    "shadow": {
                                      "type": "boolean"
                                    },
                                    "autoContrast": {
                                      "type": "boolean"
                                    }
                                  }
                                }
                              },
                              "image": {
                                "type": "object",
                                "required": [
                                  "crop",
                                  "rotate",
                                  "flipX",
                                  "flipY",
                                  "border",
                                  "borderColor",
                                  "footer"
                                ],
                                "properties": {
                                  "crop": {
                                    "type": "object",
                                    "required": [
                                      "x",
                                      "y",
                                      "width",
                                      "height"
                                    ],
                                    "properties": {
                                      "x": {
                                        "type": "number"
                                      },
                                      "y": {
                                        "type": "number"
                                      },
                                      "width": {
                                        "type": "number"
                                      },
                                      "height": {
                                        "type": "number"
                                      }
                                    }
                                  },
                                  "rotate": {
                                    "type": "number"
                                  },
                                  "flipX": {
                                    "type": "boolean"
                                  },
                                  "flipY": {
                                    "type": "boolean"
                                  },
                                  "border": {
                                    "type": "number"
                                  },
                                  "borderColor": {
                                    "type": "string"
                                  },
                                  "footer": {
                                    "type": "number"
                                  }
                                }
                              },
                              "date": {
                                "type": "object",
                                "required": [
                                  "source",
                                  "custom",
                                  "format",
                                  "missing",
                                  "offsetMinutes"
                                ],
                                "properties": {
                                  "source": {
                                    "type": "string"
                                  },
                                  "custom": {
                                    "type": "string"
                                  },
                                  "format": {
                                    "type": "string"
                                  },
                                  "missing": {
                                    "type": "string"
                                  },
                                  "offsetMinutes": {
                                    "type": "number"
                                  }
                                }
                              },
                              "sequence": {
                                "type": "object",
                                "required": [
                                  "start",
                                  "padding"
                                ],
                                "properties": {
                                  "start": {
                                    "type": "number"
                                  },
                                  "padding": {
                                    "type": "number"
                                  }
                                }
                              },
                              "frame": {
                                "type": "object",
                                "required": [
                                  "enabled"
                                ],
                                "properties": {
                                  "enabled": {
                                    "type": "boolean"
                                  }
                                }
                              },
                              "output": {
                                "type": "object",
                                "required": [
                                  "format",
                                  "quality",
                                  "longEdge",
                                  "prefix",
                                  "suffix",
                                  "metadata",
                                  "variants"
                                ],
                                "properties": {
                                  "format": {
                                    "type": "string"
                                  },
                                  "quality": {
                                    "type": "number"
                                  },
                                  "longEdge": {
                                    "type": "number"
                                  },
                                  "prefix": {
                                    "type": "string"
                                  },
                                  "suffix": {
                                    "type": "string"
                                  },
                                  "metadata": {
                                    "type": "string"
                                  },
                                  "variants": {
                                    "type": "array",
                                    "items": {}
                                  }
                                }
                              }
                            }
                          }
                        }
                      }
                    },
                    "variables": {
                      "type": "array",
                      "items": {
                        "type": "string"
                      }
                    }
                  }
                },
                "example": {
                  "version": 1,
                  "schema": "/api/v1/recipe.schema.json",
                  "templates": [
                    {
                      "id": "watermark",
                      "recipeUrl": "/api/v1/recipes/watermark.json",
                      "recipe": {
                        "version": 1,
                        "layers": [
                          {
                            "id": "watermark-text",
                            "type": "text",
                            "text": "© Your name",
                            "assetId": "",
                            "fontFamily": "Arial",
                            "weight": "600",
                            "size": 4,
                            "color": "#ffffff",
                            "opacity": 0.7,
                            "angle": 0,
                            "position": "bottom-right",
                            "x": 0.5,
                            "y": 0.5,
                            "margin": 4,
                            "tiled": false,
                            "gap": 14,
                            "stroke": false,
                            "shadow": true,
                            "autoContrast": false
                          }
                        ],
                        "image": {
                          "crop": {
                            "x": 0,
                            "y": 0,
                            "width": 1,
                            "height": 1
                          },
                          "rotate": 0,
                          "flipX": false,
                          "flipY": false,
                          "border": 0,
                          "borderColor": "#ffffff",
                          "footer": 0
                        },
                        "date": {
                          "source": "exif",
                          "custom": "",
                          "format": "YYYY-MM-DD",
                          "missing": "skip",
                          "offsetMinutes": 0
                        },
                        "sequence": {
                          "start": 1,
                          "padding": 3
                        },
                        "frame": {
                          "enabled": false
                        },
                        "output": {
                          "format": "image/jpeg",
                          "quality": 0.92,
                          "longEdge": 0,
                          "prefix": "",
                          "suffix": "-watermarked",
                          "metadata": "strip",
                          "variants": []
                        }
                      }
                    },
                    {
                      "id": "filename",
                      "recipeUrl": "/api/v1/recipes/filename.json",
                      "recipe": {
                        "version": 1,
                        "layers": [
                          {
                            "id": "filename-text",
                            "type": "text",
                            "text": "{filename}",
                            "assetId": "",
                            "fontFamily": "Arial",
                            "weight": "600",
                            "size": 4,
                            "color": "#202b48",
                            "opacity": 0.7,
                            "angle": 0,
                            "position": "footer",
                            "x": 0.5,
                            "y": 0.5,
                            "margin": 4,
                            "tiled": false,
                            "gap": 14,
                            "stroke": false,
                            "shadow": false,
                            "autoContrast": false
                          }
                        ],
                        "image": {
                          "crop": {
                            "x": 0,
                            "y": 0,
                            "width": 1,
                            "height": 1
                          },
                          "rotate": 0,
                          "flipX": false,
                          "flipY": false,
                          "border": 0,
                          "borderColor": "#ffffff",
                          "footer": 12
                        },
                        "date": {
                          "source": "exif",
                          "custom": "",
                          "format": "YYYY-MM-DD",
                          "missing": "skip",
                          "offsetMinutes": 0
                        },
                        "sequence": {
                          "start": 1,
                          "padding": 3
                        },
                        "frame": {
                          "enabled": false
                        },
                        "output": {
                          "format": "image/jpeg",
                          "quality": 0.92,
                          "longEdge": 0,
                          "prefix": "",
                          "suffix": "-watermarked",
                          "metadata": "strip",
                          "variants": []
                        }
                      }
                    },
                    {
                      "id": "date",
                      "recipeUrl": "/api/v1/recipes/date.json",
                      "recipe": {
                        "version": 1,
                        "layers": [
                          {
                            "id": "date-text",
                            "type": "text",
                            "text": "{date}",
                            "assetId": "",
                            "fontFamily": "monospace",
                            "weight": "600",
                            "size": 4,
                            "color": "#ffb34d",
                            "opacity": 0.7,
                            "angle": 0,
                            "position": "bottom-right",
                            "x": 0.5,
                            "y": 0.5,
                            "margin": 4,
                            "tiled": false,
                            "gap": 14,
                            "stroke": false,
                            "shadow": true,
                            "autoContrast": false
                          }
                        ],
                        "image": {
                          "crop": {
                            "x": 0,
                            "y": 0,
                            "width": 1,
                            "height": 1
                          },
                          "rotate": 0,
                          "flipX": false,
                          "flipY": false,
                          "border": 0,
                          "borderColor": "#ffffff",
                          "footer": 0
                        },
                        "date": {
                          "source": "exif",
                          "custom": "",
                          "format": "YYYY-MM-DD",
                          "missing": "skip",
                          "offsetMinutes": 0
                        },
                        "sequence": {
                          "start": 1,
                          "padding": 3
                        },
                        "frame": {
                          "enabled": false
                        },
                        "output": {
                          "format": "image/jpeg",
                          "quality": 0.92,
                          "longEdge": 0,
                          "prefix": "",
                          "suffix": "-watermarked",
                          "metadata": "strip",
                          "variants": []
                        }
                      }
                    },
                    {
                      "id": "frame",
                      "recipeUrl": "/api/v1/recipes/frame.json",
                      "recipe": {
                        "version": 1,
                        "layers": [
                          {
                            "id": "frame-text",
                            "type": "text",
                            "text": "© Your name",
                            "assetId": "",
                            "fontFamily": "Arial",
                            "weight": "600",
                            "size": 4,
                            "color": "#ffffff",
                            "opacity": 0.7,
                            "angle": 0,
                            "position": "bottom-right",
                            "x": 0.5,
                            "y": 0.5,
                            "margin": 4,
                            "tiled": false,
                            "gap": 14,
                            "stroke": false,
                            "shadow": true,
                            "autoContrast": false
                          }
                        ],
                        "image": {
                          "crop": {
                            "x": 0,
                            "y": 0,
                            "width": 1,
                            "height": 1
                          },
                          "rotate": 0,
                          "flipX": false,
                          "flipY": false,
                          "border": 0,
                          "borderColor": "#ffffff",
                          "footer": 0
                        },
                        "date": {
                          "source": "exif",
                          "custom": "",
                          "format": "YYYY-MM-DD",
                          "missing": "skip",
                          "offsetMinutes": 0
                        },
                        "sequence": {
                          "start": 1,
                          "padding": 3
                        },
                        "frame": {
                          "enabled": true
                        },
                        "output": {
                          "format": "image/jpeg",
                          "quality": 0.92,
                          "longEdge": 0,
                          "prefix": "",
                          "suffix": "-watermarked",
                          "metadata": "strip",
                          "variants": []
                        }
                      }
                    }
                  ],
                  "variables": [
                    "filename",
                    "fullname",
                    "index",
                    "date",
                    "label",
                    "camera",
                    "lens",
                    "aperture",
                    "iso",
                    "shutter",
                    "focal"
                  ]
                }
              }
            }
          }
        }
      }
    },
    "/api/v1/recipe.schema.json": {
      "get": {
        "operationId": "_api_v1_recipe_schema_json",
        "summary": "Local Watermark Recipe v1",
        "responses": {
          "200": {
            "description": "Static public JSON; no photo data.",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "$schema",
                    "$id",
                    "title",
                    "description",
                    "type",
                    "required",
                    "properties",
                    "additionalProperties"
                  ],
                  "properties": {
                    "$schema": {
                      "type": "string"
                    },
                    "$id": {
                      "type": "string"
                    },
                    "title": {
                      "type": "string"
                    },
                    "description": {
                      "type": "string"
                    },
                    "type": {
                      "type": "string"
                    },
                    "required": {
                      "type": "array",
                      "items": {
                        "type": "string"
                      }
                    },
                    "properties": {
                      "type": "object",
                      "required": [
                        "version",
                        "layers",
                        "image",
                        "date",
                        "sequence",
                        "frame",
                        "output"
                      ],
                      "properties": {
                        "version": {
                          "type": "object",
                          "required": [
                            "const"
                          ],
                          "properties": {
                            "const": {
                              "type": "number"
                            }
                          }
                        },
                        "layers": {
                          "type": "object",
                          "required": [
                            "type",
                            "maxItems",
                            "items"
                          ],
                          "properties": {
                            "type": {
                              "type": "string"
                            },
                            "maxItems": {
                              "type": "number"
                            },
                            "items": {
                              "type": "object",
                              "required": [
                                "type",
                                "required",
                                "properties",
                                "additionalProperties"
                              ],
                              "properties": {
                                "type": {
                                  "type": "string"
                                },
                                "required": {
                                  "type": "array",
                                  "items": {
                                    "type": "string"
                                  }
                                },
                                "properties": {
                                  "type": "object",
                                  "required": [
                                    "id",
                                    "type",
                                    "text",
                                    "assetId",
                                    "fontFamily",
                                    "weight",
                                    "size",
                                    "color",
                                    "opacity",
                                    "angle",
                                    "position",
                                    "x",
                                    "y",
                                    "margin",
                                    "tiled",
                                    "gap",
                                    "stroke",
                                    "shadow",
                                    "autoContrast"
                                  ],
                                  "properties": {
                                    "id": {
                                      "type": "object",
                                      "required": [
                                        "type",
                                        "pattern"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        },
                                        "pattern": {
                                          "type": "string"
                                        }
                                      }
                                    },
                                    "type": {
                                      "type": "object",
                                      "required": [
                                        "type",
                                        "enum"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        },
                                        "enum": {
                                          "type": "array",
                                          "items": {
                                            "type": "string"
                                          }
                                        }
                                      }
                                    },
                                    "text": {
                                      "type": "object",
                                      "required": [
                                        "type",
                                        "maxLength"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        },
                                        "maxLength": {
                                          "type": "number"
                                        }
                                      }
                                    },
                                    "assetId": {
                                      "type": "object",
                                      "required": [
                                        "type",
                                        "maxLength"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        },
                                        "maxLength": {
                                          "type": "number"
                                        }
                                      }
                                    },
                                    "fontFamily": {
                                      "type": "object",
                                      "required": [
                                        "type",
                                        "maxLength",
                                        "pattern"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        },
                                        "maxLength": {
                                          "type": "number"
                                        },
                                        "pattern": {
                                          "type": "string"
                                        }
                                      }
                                    },
                                    "weight": {
                                      "type": "object",
                                      "required": [
                                        "type",
                                        "enum"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        },
                                        "enum": {
                                          "type": "array",
                                          "items": {
                                            "type": "string"
                                          }
                                        }
                                      }
                                    },
                                    "size": {
                                      "type": "object",
                                      "required": [
                                        "type",
                                        "minimum",
                                        "maximum"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        },
                                        "minimum": {
                                          "type": "number"
                                        },
                                        "maximum": {
                                          "type": "number"
                                        }
                                      }
                                    },
                                    "color": {
                                      "type": "object",
                                      "required": [
                                        "type",
                                        "pattern"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        },
                                        "pattern": {
                                          "type": "string"
                                        }
                                      }
                                    },
                                    "opacity": {
                                      "type": "object",
                                      "required": [
                                        "type",
                                        "minimum",
                                        "maximum"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        },
                                        "minimum": {
                                          "type": "number"
                                        },
                                        "maximum": {
                                          "type": "number"
                                        }
                                      }
                                    },
                                    "angle": {
                                      "type": "object",
                                      "required": [
                                        "type",
                                        "minimum",
                                        "maximum"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        },
                                        "minimum": {
                                          "type": "number"
                                        },
                                        "maximum": {
                                          "type": "number"
                                        }
                                      }
                                    },
                                    "position": {
                                      "type": "object",
                                      "required": [
                                        "type",
                                        "enum"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        },
                                        "enum": {
                                          "type": "array",
                                          "items": {
                                            "type": "string"
                                          }
                                        }
                                      }
                                    },
                                    "x": {
                                      "type": "object",
                                      "required": [
                                        "type",
                                        "minimum",
                                        "maximum"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        },
                                        "minimum": {
                                          "type": "number"
                                        },
                                        "maximum": {
                                          "type": "number"
                                        }
                                      }
                                    },
                                    "y": {
                                      "type": "object",
                                      "required": [
                                        "type",
                                        "minimum",
                                        "maximum"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        },
                                        "minimum": {
                                          "type": "number"
                                        },
                                        "maximum": {
                                          "type": "number"
                                        }
                                      }
                                    },
                                    "margin": {
                                      "type": "object",
                                      "required": [
                                        "type",
                                        "minimum",
                                        "maximum"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        },
                                        "minimum": {
                                          "type": "number"
                                        },
                                        "maximum": {
                                          "type": "number"
                                        }
                                      }
                                    },
                                    "tiled": {
                                      "type": "object",
                                      "required": [
                                        "type"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        }
                                      }
                                    },
                                    "gap": {
                                      "type": "object",
                                      "required": [
                                        "type",
                                        "minimum",
                                        "maximum"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        },
                                        "minimum": {
                                          "type": "number"
                                        },
                                        "maximum": {
                                          "type": "number"
                                        }
                                      }
                                    },
                                    "stroke": {
                                      "type": "object",
                                      "required": [
                                        "type"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        }
                                      }
                                    },
                                    "shadow": {
                                      "type": "object",
                                      "required": [
                                        "type"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        }
                                      }
                                    },
                                    "autoContrast": {
                                      "type": "object",
                                      "required": [
                                        "type"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        }
                                      }
                                    }
                                  }
                                },
                                "additionalProperties": {
                                  "type": "boolean"
                                }
                              }
                            }
                          }
                        },
                        "image": {
                          "type": "object",
                          "required": [
                            "type",
                            "required",
                            "properties",
                            "additionalProperties"
                          ],
                          "properties": {
                            "type": {
                              "type": "string"
                            },
                            "required": {
                              "type": "array",
                              "items": {
                                "type": "string"
                              }
                            },
                            "properties": {
                              "type": "object",
                              "required": [
                                "crop",
                                "rotate",
                                "flipX",
                                "flipY",
                                "border",
                                "borderColor",
                                "footer"
                              ],
                              "properties": {
                                "crop": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "required",
                                    "properties",
                                    "additionalProperties"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "required": {
                                      "type": "array",
                                      "items": {
                                        "type": "string"
                                      }
                                    },
                                    "properties": {
                                      "type": "object",
                                      "required": [
                                        "x",
                                        "y",
                                        "width",
                                        "height",
                                        "aspectRatio"
                                      ],
                                      "properties": {
                                        "x": {
                                          "type": "object",
                                          "required": [
                                            "type",
                                            "minimum",
                                            "maximum"
                                          ],
                                          "properties": {
                                            "type": {
                                              "type": "string"
                                            },
                                            "minimum": {
                                              "type": "number"
                                            },
                                            "maximum": {
                                              "type": "number"
                                            }
                                          }
                                        },
                                        "y": {
                                          "type": "object",
                                          "required": [
                                            "type",
                                            "minimum",
                                            "maximum"
                                          ],
                                          "properties": {
                                            "type": {
                                              "type": "string"
                                            },
                                            "minimum": {
                                              "type": "number"
                                            },
                                            "maximum": {
                                              "type": "number"
                                            }
                                          }
                                        },
                                        "width": {
                                          "type": "object",
                                          "required": [
                                            "type",
                                            "minimum",
                                            "maximum",
                                            "exclusiveMinimum"
                                          ],
                                          "properties": {
                                            "type": {
                                              "type": "string"
                                            },
                                            "minimum": {
                                              "type": "number"
                                            },
                                            "maximum": {
                                              "type": "number"
                                            },
                                            "exclusiveMinimum": {
                                              "type": "number"
                                            }
                                          }
                                        },
                                        "height": {
                                          "type": "object",
                                          "required": [
                                            "type",
                                            "minimum",
                                            "maximum",
                                            "exclusiveMinimum"
                                          ],
                                          "properties": {
                                            "type": {
                                              "type": "string"
                                            },
                                            "minimum": {
                                              "type": "number"
                                            },
                                            "maximum": {
                                              "type": "number"
                                            },
                                            "exclusiveMinimum": {
                                              "type": "number"
                                            }
                                          }
                                        },
                                        "aspectRatio": {
                                          "type": "object",
                                          "required": [
                                            "type",
                                            "minimum",
                                            "maximum",
                                            "description"
                                          ],
                                          "properties": {
                                            "type": {
                                              "type": "string"
                                            },
                                            "minimum": {
                                              "type": "number"
                                            },
                                            "maximum": {
                                              "type": "number"
                                            },
                                            "description": {
                                              "type": "string"
                                            }
                                          }
                                        }
                                      }
                                    },
                                    "additionalProperties": {
                                      "type": "boolean"
                                    }
                                  }
                                },
                                "rotate": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "enum"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "enum": {
                                      "type": "array",
                                      "items": {
                                        "type": "number"
                                      }
                                    }
                                  }
                                },
                                "flipX": {
                                  "type": "object",
                                  "required": [
                                    "type"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    }
                                  }
                                },
                                "flipY": {
                                  "type": "object",
                                  "required": [
                                    "type"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    }
                                  }
                                },
                                "border": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "minimum",
                                    "maximum"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "minimum": {
                                      "type": "number"
                                    },
                                    "maximum": {
                                      "type": "number"
                                    }
                                  }
                                },
                                "borderColor": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "pattern"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "pattern": {
                                      "type": "string"
                                    }
                                  }
                                },
                                "footer": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "minimum",
                                    "maximum"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "minimum": {
                                      "type": "number"
                                    },
                                    "maximum": {
                                      "type": "number"
                                    }
                                  }
                                }
                              }
                            },
                            "additionalProperties": {
                              "type": "boolean"
                            }
                          }
                        },
                        "date": {
                          "type": "object",
                          "required": [
                            "type",
                            "required",
                            "properties",
                            "additionalProperties"
                          ],
                          "properties": {
                            "type": {
                              "type": "string"
                            },
                            "required": {
                              "type": "array",
                              "items": {
                                "type": "string"
                              }
                            },
                            "properties": {
                              "type": "object",
                              "required": [
                                "source",
                                "custom",
                                "format",
                                "missing",
                                "offsetMinutes"
                              ],
                              "properties": {
                                "source": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "enum"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "enum": {
                                      "type": "array",
                                      "items": {
                                        "type": "string"
                                      }
                                    }
                                  }
                                },
                                "custom": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "maxLength"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "maxLength": {
                                      "type": "number"
                                    }
                                  }
                                },
                                "format": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "enum"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "enum": {
                                      "type": "array",
                                      "items": {
                                        "type": "string"
                                      }
                                    }
                                  }
                                },
                                "missing": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "enum"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "enum": {
                                      "type": "array",
                                      "items": {
                                        "type": "string"
                                      }
                                    }
                                  }
                                },
                                "offsetMinutes": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "minimum",
                                    "maximum"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "minimum": {
                                      "type": "number"
                                    },
                                    "maximum": {
                                      "type": "number"
                                    }
                                  }
                                }
                              }
                            },
                            "additionalProperties": {
                              "type": "boolean"
                            }
                          }
                        },
                        "sequence": {
                          "type": "object",
                          "required": [
                            "type",
                            "required",
                            "properties",
                            "additionalProperties"
                          ],
                          "properties": {
                            "type": {
                              "type": "string"
                            },
                            "required": {
                              "type": "array",
                              "items": {
                                "type": "string"
                              }
                            },
                            "properties": {
                              "type": "object",
                              "required": [
                                "start",
                                "padding"
                              ],
                              "properties": {
                                "start": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "minimum"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "minimum": {
                                      "type": "number"
                                    }
                                  }
                                },
                                "padding": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "minimum",
                                    "maximum"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "minimum": {
                                      "type": "number"
                                    },
                                    "maximum": {
                                      "type": "number"
                                    }
                                  }
                                }
                              }
                            },
                            "additionalProperties": {
                              "type": "boolean"
                            }
                          }
                        },
                        "frame": {
                          "type": "object",
                          "required": [
                            "type",
                            "required",
                            "properties",
                            "additionalProperties"
                          ],
                          "properties": {
                            "type": {
                              "type": "string"
                            },
                            "required": {
                              "type": "array",
                              "items": {
                                "type": "string"
                              }
                            },
                            "properties": {
                              "type": "object",
                              "required": [
                                "enabled"
                              ],
                              "properties": {
                                "enabled": {
                                  "type": "object",
                                  "required": [
                                    "type"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    }
                                  }
                                }
                              }
                            },
                            "additionalProperties": {
                              "type": "boolean"
                            }
                          }
                        },
                        "output": {
                          "type": "object",
                          "required": [
                            "type",
                            "required",
                            "properties",
                            "additionalProperties"
                          ],
                          "properties": {
                            "type": {
                              "type": "string"
                            },
                            "required": {
                              "type": "array",
                              "items": {
                                "type": "string"
                              }
                            },
                            "properties": {
                              "type": "object",
                              "required": [
                                "format",
                                "quality",
                                "longEdge",
                                "prefix",
                                "suffix",
                                "metadata",
                                "variants"
                              ],
                              "properties": {
                                "format": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "enum"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "enum": {
                                      "type": "array",
                                      "items": {
                                        "type": "string"
                                      }
                                    }
                                  }
                                },
                                "quality": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "minimum",
                                    "maximum"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "minimum": {
                                      "type": "number"
                                    },
                                    "maximum": {
                                      "type": "number"
                                    }
                                  }
                                },
                                "longEdge": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "minimum",
                                    "maximum"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "minimum": {
                                      "type": "number"
                                    },
                                    "maximum": {
                                      "type": "number"
                                    }
                                  }
                                },
                                "prefix": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "maxLength"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "maxLength": {
                                      "type": "number"
                                    }
                                  }
                                },
                                "suffix": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "maxLength"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "maxLength": {
                                      "type": "number"
                                    }
                                  }
                                },
                                "metadata": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "enum"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "enum": {
                                      "type": "array",
                                      "items": {
                                        "type": "string"
                                      }
                                    }
                                  }
                                },
                                "variants": {
                                  "type": "object",
                                  "required": [
                                    "type",
                                    "maxItems",
                                    "items"
                                  ],
                                  "properties": {
                                    "type": {
                                      "type": "string"
                                    },
                                    "maxItems": {
                                      "type": "number"
                                    },
                                    "items": {
                                      "type": "object",
                                      "required": [
                                        "type",
                                        "minimum",
                                        "maximum"
                                      ],
                                      "properties": {
                                        "type": {
                                          "type": "string"
                                        },
                                        "minimum": {
                                          "type": "number"
                                        },
                                        "maximum": {
                                          "type": "number"
                                        }
                                      }
                                    }
                                  }
                                }
                              }
                            },
                            "additionalProperties": {
                              "type": "boolean"
                            }
                          }
                        }
                      }
                    },
                    "additionalProperties": {
                      "type": "boolean"
                    }
                  }
                },
                "example": {
                  "$schema": "https://json-schema.org/draft/2020-12/schema",
                  "$id": "https://watermark.noxxxx.com/api/v1/recipe.schema.json",
                  "title": "Local Watermark Recipe v1",
                  "description": "Portable settings only; no image bytes. Also call validateRecipe: unique layer IDs and crop sums require semantic validation. Logo assets and custom fonts must be supplied separately.",
                  "type": "object",
                  "required": [
                    "version",
                    "layers",
                    "image",
                    "date",
                    "sequence",
                    "frame",
                    "output"
                  ],
                  "properties": {
                    "version": {
                      "const": 1
                    },
                    "layers": {
                      "type": "array",
                      "maxItems": 30,
                      "items": {
                        "type": "object",
                        "required": [
                          "id",
                          "type",
                          "text",
                          "assetId",
                          "fontFamily",
                          "weight",
                          "size",
                          "color",
                          "opacity",
                          "angle",
                          "position",
                          "x",
                          "y",
                          "margin",
                          "tiled",
                          "gap",
                          "stroke",
                          "shadow",
                          "autoContrast"
                        ],
                        "properties": {
                          "id": {
                            "type": "string",
                            "pattern": "^[A-Za-z0-9_.-]{1,100}$"
                          },
                          "type": {
                            "type": "string",
                            "enum": [
                              "text",
                              "logo"
                            ]
                          },
                          "text": {
                            "type": "string",
                            "maxLength": 2000
                          },
                          "assetId": {
                            "type": "string",
                            "maxLength": 100
                          },
                          "fontFamily": {
                            "type": "string",
                            "maxLength": 100,
                            "pattern": "^[^;{}]*$"
                          },
                          "weight": {
                            "type": "string",
                            "enum": [
                              "400",
                              "500",
                              "600",
                              "700"
                            ]
                          },
                          "size": {
                            "type": "number",
                            "minimum": 0.2,
                            "maximum": 100
                          },
                          "color": {
                            "type": "string",
                            "pattern": "^#[0-9a-fA-F]{6}$"
                          },
                          "opacity": {
                            "type": "number",
                            "minimum": 0,
                            "maximum": 1
                          },
                          "angle": {
                            "type": "number",
                            "minimum": -180,
                            "maximum": 180
                          },
                          "position": {
                            "type": "string",
                            "enum": [
                              "top-left",
                              "top-center",
                              "top-right",
                              "center-left",
                              "center",
                              "center-right",
                              "bottom-left",
                              "bottom-center",
                              "bottom-right",
                              "footer",
                              "custom"
                            ]
                          },
                          "x": {
                            "type": "number",
                            "minimum": 0,
                            "maximum": 1
                          },
                          "y": {
                            "type": "number",
                            "minimum": 0,
                            "maximum": 1
                          },
                          "margin": {
                            "type": "number",
                            "minimum": 0,
                            "maximum": 45
                          },
                          "tiled": {
                            "type": "boolean"
                          },
                          "gap": {
                            "type": "number",
                            "minimum": 1,
                            "maximum": 100
                          },
                          "stroke": {
                            "type": "boolean"
                          },
                          "shadow": {
                            "type": "boolean"
                          },
                          "autoContrast": {
                            "type": "boolean"
                          }
                        },
                        "additionalProperties": false
                      }
                    },
                    "image": {
                      "type": "object",
                      "required": [
                        "crop",
                        "rotate",
                        "flipX",
                        "flipY",
                        "border",
                        "borderColor",
                        "footer"
                      ],
                      "properties": {
                        "crop": {
                          "type": "object",
                          "required": [
                            "x",
                            "y",
                            "width",
                            "height"
                          ],
                          "properties": {
                            "x": {
                              "type": "number",
                              "minimum": 0,
                              "maximum": 1
                            },
                            "y": {
                              "type": "number",
                              "minimum": 0,
                              "maximum": 1
                            },
                            "width": {
                              "type": "number",
                              "minimum": 0,
                              "maximum": 1,
                              "exclusiveMinimum": 0
                            },
                            "height": {
                              "type": "number",
                              "minimum": 0,
                              "maximum": 1,
                              "exclusiveMinimum": 0
                            },
                            "aspectRatio": {
                              "type": "number",
                              "minimum": 0.01,
                              "maximum": 100,
                              "description": "Optional width/height ratio after rotation, centered within the normalized crop per image. Borders and footers are added afterwards."
                            }
                          },
                          "additionalProperties": false
                        },
                        "rotate": {
                          "type": "integer",
                          "enum": [
                            0,
                            90,
                            180,
                            270
                          ]
                        },
                        "flipX": {
                          "type": "boolean"
                        },
                        "flipY": {
                          "type": "boolean"
                        },
                        "border": {
                          "type": "number",
                          "minimum": 0,
                          "maximum": 50
                        },
                        "borderColor": {
                          "type": "string",
                          "pattern": "^#[0-9a-fA-F]{6}$"
                        },
                        "footer": {
                          "type": "number",
                          "minimum": 0,
                          "maximum": 50
                        }
                      },
                      "additionalProperties": false
                    },
                    "date": {
                      "type": "object",
                      "required": [
                        "source",
                        "custom",
                        "format",
                        "missing",
                        "offsetMinutes"
                      ],
                      "properties": {
                        "source": {
                          "type": "string",
                          "enum": [
                            "exif",
                            "custom"
                          ]
                        },
                        "custom": {
                          "type": "string",
                          "maxLength": 40
                        },
                        "format": {
                          "type": "string",
                          "enum": [
                            "YYYY-MM-DD",
                            "DD/MM/YYYY",
                            "MM/DD/YYYY",
                            "YYYY-MM-DD HH:mm",
                            "YY.MM.DD"
                          ]
                        },
                        "missing": {
                          "type": "string",
                          "enum": [
                            "skip",
                            "custom",
                            "error"
                          ]
                        },
                        "offsetMinutes": {
                          "type": "number",
                          "minimum": -1440,
                          "maximum": 1440
                        }
                      },
                      "additionalProperties": false
                    },
                    "sequence": {
                      "type": "object",
                      "required": [
                        "start",
                        "padding"
                      ],
                      "properties": {
                        "start": {
                          "type": "integer",
                          "minimum": 0
                        },
                        "padding": {
                          "type": "integer",
                          "minimum": 1,
                          "maximum": 10
                        }
                      },
                      "additionalProperties": false
                    },
                    "frame": {
                      "type": "object",
                      "required": [
                        "enabled"
                      ],
                      "properties": {
                        "enabled": {
                          "type": "boolean"
                        }
                      },
                      "additionalProperties": false
                    },
                    "output": {
                      "type": "object",
                      "required": [
                        "format",
                        "quality",
                        "longEdge",
                        "prefix",
                        "suffix",
                        "metadata",
                        "variants"
                      ],
                      "properties": {
                        "format": {
                          "type": "string",
                          "enum": [
                            "image/jpeg",
                            "image/png",
                            "image/webp"
                          ]
                        },
                        "quality": {
                          "type": "number",
                          "minimum": 0.1,
                          "maximum": 1
                        },
                        "longEdge": {
                          "type": "number",
                          "minimum": 0,
                          "maximum": 32768
                        },
                        "prefix": {
                          "type": "string",
                          "maxLength": 100
                        },
                        "suffix": {
                          "type": "string",
                          "maxLength": 100
                        },
                        "metadata": {
                          "type": "string",
                          "enum": [
                            "strip",
                            "safe",
                            "all"
                          ]
                        },
                        "variants": {
                          "type": "array",
                          "maxItems": 6,
                          "items": {
                            "type": "integer",
                            "minimum": 32,
                            "maximum": 32768
                          }
                        }
                      },
                      "additionalProperties": false
                    }
                  },
                  "additionalProperties": false
                }
              }
            }
          }
        }
      }
    },
    "/api/v1/recipes/watermark.json": {
      "get": {
        "operationId": "_api_v1_recipes_watermark_json",
        "summary": "Read watermark.json",
        "responses": {
          "200": {
            "description": "Static public JSON; no photo data.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Recipe"
                },
                "example": {
                  "version": 1,
                  "layers": [
                    {
                      "id": "watermark-text",
                      "type": "text",
                      "text": "© Your name",
                      "assetId": "",
                      "fontFamily": "Arial",
                      "weight": "600",
                      "size": 4,
                      "color": "#ffffff",
                      "opacity": 0.7,
                      "angle": 0,
                      "position": "bottom-right",
                      "x": 0.5,
                      "y": 0.5,
                      "margin": 4,
                      "tiled": false,
                      "gap": 14,
                      "stroke": false,
                      "shadow": true,
                      "autoContrast": false
                    }
                  ],
                  "image": {
                    "crop": {
                      "x": 0,
                      "y": 0,
                      "width": 1,
                      "height": 1
                    },
                    "rotate": 0,
                    "flipX": false,
                    "flipY": false,
                    "border": 0,
                    "borderColor": "#ffffff",
                    "footer": 0
                  },
                  "date": {
                    "source": "exif",
                    "custom": "",
                    "format": "YYYY-MM-DD",
                    "missing": "skip",
                    "offsetMinutes": 0
                  },
                  "sequence": {
                    "start": 1,
                    "padding": 3
                  },
                  "frame": {
                    "enabled": false
                  },
                  "output": {
                    "format": "image/jpeg",
                    "quality": 0.92,
                    "longEdge": 0,
                    "prefix": "",
                    "suffix": "-watermarked",
                    "metadata": "strip",
                    "variants": []
                  }
                }
              }
            }
          }
        }
      }
    },
    "/api/v1/recipes/filename.json": {
      "get": {
        "operationId": "_api_v1_recipes_filename_json",
        "summary": "Read filename.json",
        "responses": {
          "200": {
            "description": "Static public JSON; no photo data.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Recipe"
                },
                "example": {
                  "version": 1,
                  "layers": [
                    {
                      "id": "filename-text",
                      "type": "text",
                      "text": "{filename}",
                      "assetId": "",
                      "fontFamily": "Arial",
                      "weight": "600",
                      "size": 4,
                      "color": "#202b48",
                      "opacity": 0.7,
                      "angle": 0,
                      "position": "footer",
                      "x": 0.5,
                      "y": 0.5,
                      "margin": 4,
                      "tiled": false,
                      "gap": 14,
                      "stroke": false,
                      "shadow": false,
                      "autoContrast": false
                    }
                  ],
                  "image": {
                    "crop": {
                      "x": 0,
                      "y": 0,
                      "width": 1,
                      "height": 1
                    },
                    "rotate": 0,
                    "flipX": false,
                    "flipY": false,
                    "border": 0,
                    "borderColor": "#ffffff",
                    "footer": 12
                  },
                  "date": {
                    "source": "exif",
                    "custom": "",
                    "format": "YYYY-MM-DD",
                    "missing": "skip",
                    "offsetMinutes": 0
                  },
                  "sequence": {
                    "start": 1,
                    "padding": 3
                  },
                  "frame": {
                    "enabled": false
                  },
                  "output": {
                    "format": "image/jpeg",
                    "quality": 0.92,
                    "longEdge": 0,
                    "prefix": "",
                    "suffix": "-watermarked",
                    "metadata": "strip",
                    "variants": []
                  }
                }
              }
            }
          }
        }
      }
    },
    "/api/v1/recipes/date.json": {
      "get": {
        "operationId": "_api_v1_recipes_date_json",
        "summary": "Read date.json",
        "responses": {
          "200": {
            "description": "Static public JSON; no photo data.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Recipe"
                },
                "example": {
                  "version": 1,
                  "layers": [
                    {
                      "id": "date-text",
                      "type": "text",
                      "text": "{date}",
                      "assetId": "",
                      "fontFamily": "monospace",
                      "weight": "600",
                      "size": 4,
                      "color": "#ffb34d",
                      "opacity": 0.7,
                      "angle": 0,
                      "position": "bottom-right",
                      "x": 0.5,
                      "y": 0.5,
                      "margin": 4,
                      "tiled": false,
                      "gap": 14,
                      "stroke": false,
                      "shadow": true,
                      "autoContrast": false
                    }
                  ],
                  "image": {
                    "crop": {
                      "x": 0,
                      "y": 0,
                      "width": 1,
                      "height": 1
                    },
                    "rotate": 0,
                    "flipX": false,
                    "flipY": false,
                    "border": 0,
                    "borderColor": "#ffffff",
                    "footer": 0
                  },
                  "date": {
                    "source": "exif",
                    "custom": "",
                    "format": "YYYY-MM-DD",
                    "missing": "skip",
                    "offsetMinutes": 0
                  },
                  "sequence": {
                    "start": 1,
                    "padding": 3
                  },
                  "frame": {
                    "enabled": false
                  },
                  "output": {
                    "format": "image/jpeg",
                    "quality": 0.92,
                    "longEdge": 0,
                    "prefix": "",
                    "suffix": "-watermarked",
                    "metadata": "strip",
                    "variants": []
                  }
                }
              }
            }
          }
        }
      }
    },
    "/api/v1/recipes/frame.json": {
      "get": {
        "operationId": "_api_v1_recipes_frame_json",
        "summary": "Read frame.json",
        "responses": {
          "200": {
            "description": "Static public JSON; no photo data.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Recipe"
                },
                "example": {
                  "version": 1,
                  "layers": [
                    {
                      "id": "frame-text",
                      "type": "text",
                      "text": "© Your name",
                      "assetId": "",
                      "fontFamily": "Arial",
                      "weight": "600",
                      "size": 4,
                      "color": "#ffffff",
                      "opacity": 0.7,
                      "angle": 0,
                      "position": "bottom-right",
                      "x": 0.5,
                      "y": 0.5,
                      "margin": 4,
                      "tiled": false,
                      "gap": 14,
                      "stroke": false,
                      "shadow": true,
                      "autoContrast": false
                    }
                  ],
                  "image": {
                    "crop": {
                      "x": 0,
                      "y": 0,
                      "width": 1,
                      "height": 1
                    },
                    "rotate": 0,
                    "flipX": false,
                    "flipY": false,
                    "border": 0,
                    "borderColor": "#ffffff",
                    "footer": 0
                  },
                  "date": {
                    "source": "exif",
                    "custom": "",
                    "format": "YYYY-MM-DD",
                    "missing": "skip",
                    "offsetMinutes": 0
                  },
                  "sequence": {
                    "start": 1,
                    "padding": 3
                  },
                  "frame": {
                    "enabled": true
                  },
                  "output": {
                    "format": "image/jpeg",
                    "quality": 0.92,
                    "longEdge": 0,
                    "prefix": "",
                    "suffix": "-watermarked",
                    "metadata": "strip",
                    "variants": []
                  }
                }
              }
            }
          }
        }
      }
    },
    "/api/v1/mcp-tools.json": {
      "get": {
        "operationId": "_api_v1_mcp_tools_json",
        "summary": "Read mcp-tools.json",
        "responses": {
          "200": {
            "description": "Static public JSON; no photo data.",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "transport",
                    "hostedEndpoint",
                    "tools"
                  ],
                  "properties": {
                    "transport": {
                      "type": "string"
                    },
                    "hostedEndpoint": {
                      "type": "null"
                    },
                    "tools": {
                      "type": "array",
                      "items": {
                        "anyOf": [
                          {
                            "type": "object",
                            "required": [
                              "name",
                              "description",
                              "inputSchema",
                              "annotations",
                              "result"
                            ],
                            "properties": {
                              "name": {
                                "type": "string"
                              },
                              "description": {
                                "type": "string"
                              },
                              "inputSchema": {
                                "type": "object",
                                "required": [
                                  "$schema",
                                  "type",
                                  "properties",
                                  "required",
                                  "additionalProperties"
                                ],
                                "properties": {
                                  "$schema": {
                                    "type": "string"
                                  },
                                  "type": {
                                    "type": "string"
                                  },
                                  "properties": {
                                    "type": "object",
                                    "required": [
                                      "recipe"
                                    ],
                                    "properties": {
                                      "recipe": {
                                        "type": "object",
                                        "required": [
                                          "type",
                                          "properties",
                                          "additionalProperties"
                                        ],
                                        "properties": {
                                          "type": {
                                            "type": "string"
                                          },
                                          "properties": {
                                            "type": "object",
                                            "required": [],
                                            "properties": {}
                                          },
                                          "additionalProperties": {
                                            "type": "object",
                                            "required": [],
                                            "properties": {}
                                          }
                                        }
                                      }
                                    }
                                  },
                                  "required": {
                                    "type": "array",
                                    "items": {
                                      "type": "string"
                                    }
                                  },
                                  "additionalProperties": {
                                    "type": "boolean"
                                  }
                                }
                              },
                              "annotations": {
                                "type": "object",
                                "required": [
                                  "readOnlyHint"
                                ],
                                "properties": {
                                  "readOnlyHint": {
                                    "type": "boolean"
                                  }
                                }
                              },
                              "result": {
                                "type": "string"
                              }
                            }
                          },
                          {
                            "type": "object",
                            "required": [
                              "name",
                              "description",
                              "inputSchema",
                              "annotations",
                              "result"
                            ],
                            "properties": {
                              "name": {
                                "type": "string"
                              },
                              "description": {
                                "type": "string"
                              },
                              "inputSchema": {
                                "type": "object",
                                "required": [
                                  "$schema",
                                  "type",
                                  "properties",
                                  "required",
                                  "additionalProperties"
                                ],
                                "properties": {
                                  "$schema": {
                                    "type": "string"
                                  },
                                  "type": {
                                    "type": "string"
                                  },
                                  "properties": {
                                    "type": "object",
                                    "required": [
                                      "files"
                                    ],
                                    "properties": {
                                      "files": {
                                        "type": "object",
                                        "required": [
                                          "type",
                                          "minItems",
                                          "items"
                                        ],
                                        "properties": {
                                          "type": {
                                            "type": "string"
                                          },
                                          "minItems": {
                                            "type": "number"
                                          },
                                          "items": {
                                            "type": "object",
                                            "required": [
                                              "type"
                                            ],
                                            "properties": {
                                              "type": {
                                                "type": "string"
                                              }
                                            }
                                          }
                                        }
                                      }
                                    }
                                  },
                                  "required": {
                                    "type": "array",
                                    "items": {
                                      "type": "string"
                                    }
                                  },
                                  "additionalProperties": {
                                    "type": "boolean"
                                  }
                                }
                              },
                              "annotations": {
                                "type": "object",
                                "required": [
                                  "readOnlyHint",
                                  "destructiveHint"
                                ],
                                "properties": {
                                  "readOnlyHint": {
                                    "type": "boolean"
                                  },
                                  "destructiveHint": {
                                    "type": "boolean"
                                  }
                                }
                              },
                              "result": {
                                "type": "string"
                              }
                            }
                          },
                          {
                            "type": "object",
                            "required": [
                              "name",
                              "description",
                              "inputSchema",
                              "annotations",
                              "result"
                            ],
                            "properties": {
                              "name": {
                                "type": "string"
                              },
                              "description": {
                                "type": "string"
                              },
                              "inputSchema": {
                                "type": "object",
                                "required": [
                                  "$schema",
                                  "type",
                                  "properties",
                                  "required",
                                  "additionalProperties"
                                ],
                                "properties": {
                                  "$schema": {
                                    "type": "string"
                                  },
                                  "type": {
                                    "type": "string"
                                  },
                                  "properties": {
                                    "type": "object",
                                    "required": [
                                      "files",
                                      "recipe",
                                      "output",
                                      "logos"
                                    ],
                                    "properties": {
                                      "files": {
                                        "type": "object",
                                        "required": [
                                          "type",
                                          "minItems",
                                          "items"
                                        ],
                                        "properties": {
                                          "type": {
                                            "type": "string"
                                          },
                                          "minItems": {
                                            "type": "number"
                                          },
                                          "items": {
                                            "type": "object",
                                            "required": [
                                              "type"
                                            ],
                                            "properties": {
                                              "type": {
                                                "type": "string"
                                              }
                                            }
                                          }
                                        }
                                      },
                                      "recipe": {
                                        "type": "object",
                                        "required": [
                                          "type",
                                          "properties",
                                          "additionalProperties"
                                        ],
                                        "properties": {
                                          "type": {
                                            "type": "string"
                                          },
                                          "properties": {
                                            "type": "object",
                                            "required": [],
                                            "properties": {}
                                          },
                                          "additionalProperties": {
                                            "type": "object",
                                            "required": [],
                                            "properties": {}
                                          }
                                        }
                                      },
                                      "output": {
                                        "type": "object",
                                        "required": [
                                          "type"
                                        ],
                                        "properties": {
                                          "type": {
                                            "type": "string"
                                          }
                                        }
                                      },
                                      "logos": {
                                        "type": "object",
                                        "required": [
                                          "type",
                                          "properties",
                                          "additionalProperties"
                                        ],
                                        "properties": {
                                          "type": {
                                            "type": "string"
                                          },
                                          "properties": {
                                            "type": "object",
                                            "required": [],
                                            "properties": {}
                                          },
                                          "additionalProperties": {
                                            "type": "object",
                                            "required": [
                                              "type"
                                            ],
                                            "properties": {
                                              "type": {
                                                "type": "string"
                                              }
                                            }
                                          }
                                        }
                                      }
                                    }
                                  },
                                  "required": {
                                    "type": "array",
                                    "items": {
                                      "type": "string"
                                    }
                                  },
                                  "additionalProperties": {
                                    "type": "boolean"
                                  }
                                }
                              },
                              "annotations": {
                                "type": "object",
                                "required": [
                                  "readOnlyHint",
                                  "destructiveHint"
                                ],
                                "properties": {
                                  "readOnlyHint": {
                                    "type": "boolean"
                                  },
                                  "destructiveHint": {
                                    "type": "boolean"
                                  }
                                }
                              },
                              "result": {
                                "type": "string"
                              }
                            }
                          }
                        ]
                      }
                    }
                  }
                },
                "example": {
                  "transport": "stdio",
                  "hostedEndpoint": null,
                  "tools": [
                    {
                      "name": "validate_recipe",
                      "description": "Validate a local image watermark recipe without reading images.",
                      "inputSchema": {
                        "$schema": "http://json-schema.org/draft-07/schema#",
                        "type": "object",
                        "properties": {
                          "recipe": {
                            "type": "object",
                            "properties": {},
                            "additionalProperties": {}
                          }
                        },
                        "required": [
                          "recipe"
                        ],
                        "additionalProperties": false
                      },
                      "annotations": {
                        "readOnlyHint": true
                      },
                      "result": "{errors:string[]}"
                    },
                    {
                      "name": "inspect_images",
                      "description": "Read dimensions and EXIF from selected local files; return per-file inspection failures.",
                      "inputSchema": {
                        "$schema": "http://json-schema.org/draft-07/schema#",
                        "type": "object",
                        "properties": {
                          "files": {
                            "type": "array",
                            "minItems": 1,
                            "items": {
                              "type": "string"
                            }
                          }
                        },
                        "required": [
                          "files"
                        ],
                        "additionalProperties": false
                      },
                      "annotations": {
                        "readOnlyHint": true,
                        "destructiveHint": false
                      },
                      "result": "{images:[{id,name,width,height,metadata,metadataWarning}],failures:[{id,name,index,stage,message}]}"
                    },
                    {
                      "name": "preview_watermark",
                      "description": "Write a preview of only the first selected file, up to 1400px. Never overwrite originals.",
                      "inputSchema": {
                        "$schema": "http://json-schema.org/draft-07/schema#",
                        "type": "object",
                        "properties": {
                          "files": {
                            "type": "array",
                            "minItems": 1,
                            "items": {
                              "type": "string"
                            }
                          },
                          "recipe": {
                            "type": "object",
                            "properties": {},
                            "additionalProperties": {}
                          },
                          "output": {
                            "type": "string"
                          },
                          "logos": {
                            "type": "object",
                            "properties": {},
                            "additionalProperties": {
                              "type": "string"
                            }
                          }
                        },
                        "required": [
                          "files",
                          "recipe"
                        ],
                        "additionalProperties": false
                      },
                      "annotations": {
                        "readOnlyHint": false,
                        "destructiveHint": false
                      },
                      "result": "{files:[{path,width,height}],failures:[{id,name,index,stage,message,longEdge?}],cancelled:boolean}"
                    },
                    {
                      "name": "batch_watermark",
                      "description": "Write successful local watermark copies and return per-file failures. Images never upload.",
                      "inputSchema": {
                        "$schema": "http://json-schema.org/draft-07/schema#",
                        "type": "object",
                        "properties": {
                          "files": {
                            "type": "array",
                            "minItems": 1,
                            "items": {
                              "type": "string"
                            }
                          },
                          "recipe": {
                            "type": "object",
                            "properties": {},
                            "additionalProperties": {}
                          },
                          "output": {
                            "type": "string"
                          },
                          "logos": {
                            "type": "object",
                            "properties": {},
                            "additionalProperties": {
                              "type": "string"
                            }
                          }
                        },
                        "required": [
                          "files",
                          "recipe"
                        ],
                        "additionalProperties": false
                      },
                      "annotations": {
                        "readOnlyHint": false,
                        "destructiveHint": false
                      },
                      "result": "{files:[{path,width,height}],failures:[{id,name,index,stage,message,longEdge?}],cancelled:boolean}"
                    }
                  ]
                }
              }
            }
          }
        }
      }
    }
  },
  "components": {
    "schemas": {
      "Recipe": {
        "$schema": "https://json-schema.org/draft/2020-12/schema",
        "$id": "https://watermark.noxxxx.com/api/v1/recipe.schema.json",
        "title": "Local Watermark Recipe v1",
        "description": "Portable settings only; no image bytes. Also call validateRecipe: unique layer IDs and crop sums require semantic validation. Logo assets and custom fonts must be supplied separately.",
        "type": "object",
        "required": [
          "version",
          "layers",
          "image",
          "date",
          "sequence",
          "frame",
          "output"
        ],
        "properties": {
          "version": {
            "const": 1
          },
          "layers": {
            "type": "array",
            "maxItems": 30,
            "items": {
              "type": "object",
              "required": [
                "id",
                "type",
                "text",
                "assetId",
                "fontFamily",
                "weight",
                "size",
                "color",
                "opacity",
                "angle",
                "position",
                "x",
                "y",
                "margin",
                "tiled",
                "gap",
                "stroke",
                "shadow",
                "autoContrast"
              ],
              "properties": {
                "id": {
                  "type": "string",
                  "pattern": "^[A-Za-z0-9_.-]{1,100}$"
                },
                "type": {
                  "type": "string",
                  "enum": [
                    "text",
                    "logo"
                  ]
                },
                "text": {
                  "type": "string",
                  "maxLength": 2000
                },
                "assetId": {
                  "type": "string",
                  "maxLength": 100
                },
                "fontFamily": {
                  "type": "string",
                  "maxLength": 100,
                  "pattern": "^[^;{}]*$"
                },
                "weight": {
                  "type": "string",
                  "enum": [
                    "400",
                    "500",
                    "600",
                    "700"
                  ]
                },
                "size": {
                  "type": "number",
                  "minimum": 0.2,
                  "maximum": 100
                },
                "color": {
                  "type": "string",
                  "pattern": "^#[0-9a-fA-F]{6}$"
                },
                "opacity": {
                  "type": "number",
                  "minimum": 0,
                  "maximum": 1
                },
                "angle": {
                  "type": "number",
                  "minimum": -180,
                  "maximum": 180
                },
                "position": {
                  "type": "string",
                  "enum": [
                    "top-left",
                    "top-center",
                    "top-right",
                    "center-left",
                    "center",
                    "center-right",
                    "bottom-left",
                    "bottom-center",
                    "bottom-right",
                    "footer",
                    "custom"
                  ]
                },
                "x": {
                  "type": "number",
                  "minimum": 0,
                  "maximum": 1
                },
                "y": {
                  "type": "number",
                  "minimum": 0,
                  "maximum": 1
                },
                "margin": {
                  "type": "number",
                  "minimum": 0,
                  "maximum": 45
                },
                "tiled": {
                  "type": "boolean"
                },
                "gap": {
                  "type": "number",
                  "minimum": 1,
                  "maximum": 100
                },
                "stroke": {
                  "type": "boolean"
                },
                "shadow": {
                  "type": "boolean"
                },
                "autoContrast": {
                  "type": "boolean"
                }
              },
              "additionalProperties": false
            }
          },
          "image": {
            "type": "object",
            "required": [
              "crop",
              "rotate",
              "flipX",
              "flipY",
              "border",
              "borderColor",
              "footer"
            ],
            "properties": {
              "crop": {
                "type": "object",
                "required": [
                  "x",
                  "y",
                  "width",
                  "height"
                ],
                "properties": {
                  "x": {
                    "type": "number",
                    "minimum": 0,
                    "maximum": 1
                  },
                  "y": {
                    "type": "number",
                    "minimum": 0,
                    "maximum": 1
                  },
                  "width": {
                    "type": "number",
                    "minimum": 0,
                    "maximum": 1,
                    "exclusiveMinimum": 0
                  },
                  "height": {
                    "type": "number",
                    "minimum": 0,
                    "maximum": 1,
                    "exclusiveMinimum": 0
                  },
                  "aspectRatio": {
                    "type": "number",
                    "minimum": 0.01,
                    "maximum": 100,
                    "description": "Optional width/height ratio after rotation, centered within the normalized crop per image. Borders and footers are added afterwards."
                  }
                },
                "additionalProperties": false
              },
              "rotate": {
                "type": "integer",
                "enum": [
                  0,
                  90,
                  180,
                  270
                ]
              },
              "flipX": {
                "type": "boolean"
              },
              "flipY": {
                "type": "boolean"
              },
              "border": {
                "type": "number",
                "minimum": 0,
                "maximum": 50
              },
              "borderColor": {
                "type": "string",
                "pattern": "^#[0-9a-fA-F]{6}$"
              },
              "footer": {
                "type": "number",
                "minimum": 0,
                "maximum": 50
              }
            },
            "additionalProperties": false
          },
          "date": {
            "type": "object",
            "required": [
              "source",
              "custom",
              "format",
              "missing",
              "offsetMinutes"
            ],
            "properties": {
              "source": {
                "type": "string",
                "enum": [
                  "exif",
                  "custom"
                ]
              },
              "custom": {
                "type": "string",
                "maxLength": 40
              },
              "format": {
                "type": "string",
                "enum": [
                  "YYYY-MM-DD",
                  "DD/MM/YYYY",
                  "MM/DD/YYYY",
                  "YYYY-MM-DD HH:mm",
                  "YY.MM.DD"
                ]
              },
              "missing": {
                "type": "string",
                "enum": [
                  "skip",
                  "custom",
                  "error"
                ]
              },
              "offsetMinutes": {
                "type": "number",
                "minimum": -1440,
                "maximum": 1440
              }
            },
            "additionalProperties": false
          },
          "sequence": {
            "type": "object",
            "required": [
              "start",
              "padding"
            ],
            "properties": {
              "start": {
                "type": "integer",
                "minimum": 0
              },
              "padding": {
                "type": "integer",
                "minimum": 1,
                "maximum": 10
              }
            },
            "additionalProperties": false
          },
          "frame": {
            "type": "object",
            "required": [
              "enabled"
            ],
            "properties": {
              "enabled": {
                "type": "boolean"
              }
            },
            "additionalProperties": false
          },
          "output": {
            "type": "object",
            "required": [
              "format",
              "quality",
              "longEdge",
              "prefix",
              "suffix",
              "metadata",
              "variants"
            ],
            "properties": {
              "format": {
                "type": "string",
                "enum": [
                  "image/jpeg",
                  "image/png",
                  "image/webp"
                ]
              },
              "quality": {
                "type": "number",
                "minimum": 0.1,
                "maximum": 1
              },
              "longEdge": {
                "type": "number",
                "minimum": 0,
                "maximum": 32768
              },
              "prefix": {
                "type": "string",
                "maxLength": 100
              },
              "suffix": {
                "type": "string",
                "maxLength": 100
              },
              "metadata": {
                "type": "string",
                "enum": [
                  "strip",
                  "safe",
                  "all"
                ]
              },
              "variants": {
                "type": "array",
                "maxItems": 6,
                "items": {
                  "type": "integer",
                  "minimum": 32,
                  "maximum": 32768
                }
              }
            },
            "additionalProperties": false
          }
        },
        "additionalProperties": false
      }
    }
  }
}
