{
  "openapi": "3.1.0",
  "info": {
    "title": "VisionFlow Match",
    "description": "Hosted OpenCV for finding a pattern image inside a larger image: template matching, ORB/SIFT feature matching and RANSAC homography, over HTTP and MCP. Gives automation agents pixel boxes, corners and confidence for UI elements, logos and objects in screenshots. A hosted alternative to running OpenCV (opencv/opencv) yourself.",
    "version": "1.0.0"
  },
  "servers": [
    {
      "url": "https://visionflow-match.saastemly.com"
    }
  ],
  "paths": {
    "/v1/template-match": {
      "post": {
        "operationId": "template-match",
        "summary": "Find where a small pattern image (a button, icon, logo or crop) appears inside a larger screenshot or picture, using OpenCV cv2.matchTemplate.",
        "description": "Find where a small pattern image (a button, icon, logo or crop) appears inside a larger screenshot or picture, using OpenCV cv2.matchTemplate. Returns the best position, plus every non-overlapping position scoring above the threshold, as pixel boxes with scores. Use it for exact-looking pixel patterns at the same scale; for different scale, rotation or perspective use /v1/homography.\n\nPrice: $0.003 per call (x402, or prepaid credits with an API key).",
        "x-price-usd": 0.003,
        "responses": {
          "200": {
            "description": "The result",
            "content": {
              "application/json": {
                "example": {
                  "image": {
                    "width": 112,
                    "height": 84
                  },
                  "template": {
                    "width": 36,
                    "height": 28
                  },
                  "method": "TM_CCOEFF_NORMED",
                  "threshold": 0.8,
                  "found": true,
                  "best": {
                    "x": 40,
                    "y": 30,
                    "width": 36,
                    "height": 28,
                    "centerX": 58,
                    "centerY": 44,
                    "score": 1
                  },
                  "matches": [
                    {
                      "x": 40,
                      "y": 30,
                      "width": 36,
                      "height": 28,
                      "centerX": 58,
                      "centerY": 44,
                      "score": 1
                    }
                  ]
                }
              }
            }
          },
          "400": {
            "description": "The request is not valid (nothing is charged)"
          },
          "402": {
            "description": "Payment required: the x402 terms are in the PAYMENT-REQUIRED header; or send an API key"
          }
        },
        "security": [
          {},
          {
            "apiKey": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "image": {
                    "type": "string",
                    "description": "Base64 of a PNG, JPEG, BMP or WebP file (a data: URI also works). At most 4 million pixels and about 2 MB. Alpha is dropped."
                  },
                  "template": {
                    "type": "string",
                    "description": "Base64 of the pattern to find, same formats. At most 1 million pixels and about 1 MB. Must fit inside the image."
                  },
                  "method": {
                    "type": "string",
                    "enum": [
                      "TM_CCOEFF_NORMED",
                      "TM_CCORR_NORMED",
                      "TM_SQDIFF_NORMED"
                    ],
                    "description": "OpenCV matching method (default TM_CCOEFF_NORMED, robust to brightness change). Scores are 0-1, higher is better; for TM_SQDIFF_NORMED the score is 1 minus the squared-difference value"
                  },
                  "threshold": {
                    "type": "number",
                    "description": "Minimum score for a match, 0-1 (default 0.8)"
                  },
                  "max_matches": {
                    "type": "integer",
                    "description": "Most matches returned, 1-50 (default 5); overlapping positions are suppressed"
                  },
                  "grayscale": {
                    "type": "boolean",
                    "description": "Match on grayscale versions of both images (default false: match all three colour channels)"
                  }
                },
                "required": [
                  "image",
                  "template"
                ]
              },
              "example": {
                "image": "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",
                "template": "iVBORw0KGgoAAAANSUhEUgAAACQAAAAcCAAAAAAsQkKEAAAA+klEQVQ4y42SPQ6CUBCEZwktnsCOyhPYcw/tqLyAsREruAAX8AR2dvQmFlZaYeUJpNJGF/D9PyKTrLDyMcPbLNVodYLUhGsGQ4HN4Ml180GGZg7lgVwFdhp3jlUHzQ1o7gTacQd591aiRSbyzg/xfIqEf6tU9CFaKDvpHnigSmRzFXHZUWc6DFAc1Z0VXvaxl1zxzylEn/d/Th4j7LlqDSLv65WiAiICUeFCqTtMDxVLKzlxh9oqangLdiNXRVgpqBigDGj9d5hDnxSPWt/YgKy0j97Qvb9GWOl/52t5mgtvQQQ0UduXCsutzLBz6VVyrTayHT4dg01jQ19MuT6lPI4mjwAAAABJRU5ErkJggg==",
                "method": "TM_CCOEFF_NORMED",
                "threshold": 0.8,
                "max_matches": 5
              }
            }
          }
        }
      }
    },
    "/v1/feature-match": {
      "post": {
        "operationId": "feature-match",
        "summary": "Match local features between a pattern image and a larger image: detects ORB or SIFT keypoints in both, matches them with a brute-force matcher and Lowe's ratio test (OpenCV BFMatcher.knnMatch), and returns the good matches as point pairs sorted by distance.",
        "description": "Match local features between a pattern image and a larger image: detects ORB or SIFT keypoints in both, matches them with a brute-force matcher and Lowe's ratio test (OpenCV BFMatcher.knnMatch), and returns the good matches as point pairs sorted by distance. Use it to see which parts of a pattern are present and where, even when the pattern is scaled or rotated; for the pattern's outline use /v1/homography.\n\nPrice: $0.004 per call (x402, or prepaid credits with an API key).",
        "x-price-usd": 0.004,
        "responses": {
          "200": {
            "description": "The result",
            "content": {
              "application/json": {
                "example": {
                  "image": {
                    "width": 128,
                    "height": 96
                  },
                  "template": {
                    "width": 64,
                    "height": 48
                  },
                  "detector": "sift",
                  "ratio": 0.75,
                  "templateKeypoints": 33,
                  "imageKeypoints": 144,
                  "goodMatches": 21,
                  "matches": [
                    {
                      "template": {
                        "x": 36.18,
                        "y": 11.07
                      },
                      "image": {
                        "x": 79.14,
                        "y": 34.19
                      },
                      "distance": 48.43
                    },
                    {
                      "template": {
                        "x": 32.93,
                        "y": 11.54
                      },
                      "image": {
                        "x": 75.49,
                        "y": 35.26
                      },
                      "distance": 50.59
                    },
                    {
                      "template": {
                        "x": 23.66,
                        "y": 9.62
                      },
                      "image": {
                        "x": 65.2,
                        "y": 35.06
                      },
                      "distance": 51.06
                    },
                    {
                      "template": {
                        "x": 23.66,
                        "y": 9.62
                      },
                      "image": {
                        "x": 65.2,
                        "y": 35.06
                      },
                      "distance": 58.85
                    },
                    {
                      "template": {
                        "x": 48.35,
                        "y": 38.99
                      },
                      "image": {
                        "x": 97.28,
                        "y": 61.83
                      },
                      "distance": 73.48
                    },
                    {
                      "template": {
                        "x": 40.7,
                        "y": 29.71
                      },
                      "image": {
                        "x": 87.36,
                        "y": 53.5
                      },
                      "distance": 75.19
                    },
                    {
                      "template": {
                        "x": 35.88,
                        "y": 23.88
                      },
                      "image": {
                        "x": 81.02,
                        "y": 48.02
                      },
                      "distance": 85.85
                    },
                    {
                      "template": {
                        "x": 40.7,
                        "y": 29.71
                      },
                      "image": {
                        "x": 87.36,
                        "y": 53.5
                      },
                      "distance": 95.79
                    },
                    {
                      "template": {
                        "x": 9.2,
                        "y": 11.9
                      },
                      "image": {
                        "x": 50,
                        "y": 40.09
                      },
                      "distance": 97.09
                    },
                    {
                      "template": {
                        "x": 43.09,
                        "y": 18.35
                      },
                      "image": {
                        "x": 88.05,
                        "y": 40.69
                      },
                      "distance": 97.2
                    }
                  ]
                }
              }
            }
          },
          "400": {
            "description": "The request is not valid (nothing is charged)"
          },
          "402": {
            "description": "Payment required: the x402 terms are in the PAYMENT-REQUIRED header; or send an API key"
          }
        },
        "security": [
          {},
          {
            "apiKey": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "image": {
                    "type": "string",
                    "description": "Base64 of a PNG, JPEG, BMP or WebP file (a data: URI also works). At most 4 million pixels and about 2 MB. Alpha is dropped."
                  },
                  "template": {
                    "type": "string",
                    "description": "Base64 of the pattern to find, same formats. At most 1 million pixels and about 1 MB."
                  },
                  "detector": {
                    "type": "string",
                    "enum": [
                      "orb",
                      "sift"
                    ],
                    "description": "Keypoint detector and descriptor: orb (default, fast, binary descriptors, Hamming distance) or sift (slower, better with scale changes, L2 distance)"
                  },
                  "max_features": {
                    "type": "integer",
                    "description": "Most keypoints kept per image, 100-5000 (default 2000)"
                  },
                  "ratio": {
                    "type": "number",
                    "description": "Lowe's ratio test threshold, 0.5-0.95 (default 0.75): a match is kept when its distance is below ratio times the second-best distance"
                  },
                  "max_matches": {
                    "type": "integer",
                    "description": "Most matches listed, 1-200 (default 50); goodMatches always counts all of them"
                  }
                },
                "required": [
                  "image",
                  "template"
                ]
              },
              "example": {
                "image": "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",
                "template": "iVBORw0KGgoAAAANSUhEUgAAAEAAAAAwCAAAAACEICPDAAADAklEQVRIx61UT0gUURz+Znfazdyx0Ex3U1smVqJCKwn6c5FCCaKDoYdOEh7WywQiQh6UisKgS7QgLLSXQrpIdPTPISIiiAqlSHJptbINRTR1E1m3fc0b58/OOjM7rv6YefPmzft9v+/73pvHPIUUftq0ARGYxSjQIHWiysggbRzyyzS2HFJ+twLgzzV9VOlEM/Obo46MOZYKoCjQ5YsS/PYI0Jg0yBc98PvptUHAUsEhCSGqz5dM1MpHctMI6PPhsGl5A0oN+OsA9BYGg1kIJvlmDILShVAoJA+MqW1Alx9grXjfS8Px0Iklgmb3shvJmaqkC31YZV3N6hzmtfEmoPXDV4uc6yvVB98TYKWmdOGL1/2r5zmZiVfe0Cw1YxCWRNytQM9ExWlg+WMxPlV7gZ6TX9NcfcaKqACRtsgmhLT4vPhdENt2rzORLge45JrPM/02DiEa2JjH6vdAr4ZQNgt0uP+tdYj9xflHvg/fLg0nnGyyyEO/hjAk5NoHZcAel/f8C7E7XOsDQ5AACDzK95AeYPEVxqfoBCkIkTrsrr/BqVmkhi4DvoUBYJX0CsLhswKtLugkpH78SU3UyekgjAjBUBHk5e4SvCk8BZS74pUkfq4gLUbKKSiFZYDV/jXHZOJnnSaAofcC8OQWi5Er4kvfkegYCvbh+hLeDTS1btoHgzWB+zeZXsKoHGjM0vXYGOkTV6WppL/Lo3dK9oAk57l5bh2qCYxqJOS/ohtoOVp2OytfYfB5eGnveqqg5TGRUhUeeg6GITM43l7ceeFMZ5VSmqhUwhoHKwCgHvuPZThIMkhYIigAhSfAezXtDKPmh61PGhsnkrUIO0eaghDLF0BGiBki2DtUJQQ+bwmailjeANtaBYVCmDeiwMI+wtYYcAZjvH0AjqOXQcS2ZyJvlwFnqmIThSwT78jPB7TpyncZ5yw1xHIs45x0t/4eaazNayOp1Rtt2ugwyRcPl3GTmrHt/Qt8FglTAFMKvJWJJv4/079eM2dwYCd/51pzG3f0QPkPRu/dDgU3nB4AAAAASUVORK5CYII=",
                "detector": "sift",
                "ratio": 0.75,
                "max_matches": 10
              }
            }
          }
        }
      }
    },
    "/v1/homography": {
      "post": {
        "operationId": "homography",
        "summary": "Locate a pattern image inside a larger image even when it is scaled, rotated or viewed at an angle: ORB or SIFT feature matching plus cv2.findHomography with RANSAC.",
        "description": "Locate a pattern image inside a larger image even when it is scaled, rotated or viewed at an angle: ORB or SIFT feature matching plus cv2.findHomography with RANSAC. Returns whether it was found, the 3x3 homography (pattern pixels to image pixels), the four projected corners, the bounding box, and the inlier count as confidence. Use it to find a UI element, logo or object in a screenshot or photo.\n\nPrice: $0.004 per call (x402, or prepaid credits with an API key).",
        "x-price-usd": 0.004,
        "responses": {
          "200": {
            "description": "The result",
            "content": {
              "application/json": {
                "example": {
                  "image": {
                    "width": 128,
                    "height": 96
                  },
                  "template": {
                    "width": 64,
                    "height": 48
                  },
                  "detector": "sift",
                  "templateKeypoints": 33,
                  "imageKeypoints": 144,
                  "goodMatches": 21,
                  "found": true,
                  "reason": null,
                  "inliers": 21,
                  "inlierRatio": 1,
                  "homography": [
                    [
                      1.078726,
                      0.203382,
                      37.757521
                    ],
                    [
                      -0.195289,
                      1.094195,
                      29.073396
                    ],
                    [
                      -0.00001,
                      0.000163,
                      1
                    ]
                  ],
                  "corners": {
                    "topLeft": {
                      "x": 37.76,
                      "y": 29.07
                    },
                    "topRight": {
                      "x": 106.87,
                      "y": 16.59
                    },
                    "bottomRight": {
                      "x": 115.73,
                      "y": 68.6
                    },
                    "bottomLeft": {
                      "x": 47.15,
                      "y": 80.96
                    }
                  },
                  "boundingBox": {
                    "x": 37.76,
                    "y": 16.59,
                    "width": 77.97,
                    "height": 64.37
                  }
                }
              }
            }
          },
          "400": {
            "description": "The request is not valid (nothing is charged)"
          },
          "402": {
            "description": "Payment required: the x402 terms are in the PAYMENT-REQUIRED header; or send an API key"
          }
        },
        "security": [
          {},
          {
            "apiKey": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "image": {
                    "type": "string",
                    "description": "Base64 of a PNG, JPEG, BMP or WebP file (a data: URI also works). At most 4 million pixels and about 2 MB. Alpha is dropped."
                  },
                  "template": {
                    "type": "string",
                    "description": "Base64 of the pattern to find, same formats. At most 1 million pixels and about 1 MB. Needs visible texture or corners; a flat-coloured pattern has no features."
                  },
                  "detector": {
                    "type": "string",
                    "enum": [
                      "orb",
                      "sift"
                    ],
                    "description": "Keypoint detector and descriptor: orb (default, fast, binary descriptors, Hamming distance) or sift (slower, better with scale changes, L2 distance)"
                  },
                  "max_features": {
                    "type": "integer",
                    "description": "Most keypoints kept per image, 100-5000 (default 2000)"
                  },
                  "ratio": {
                    "type": "number",
                    "description": "Lowe's ratio test threshold, 0.5-0.95 (default 0.75): a match is kept when its distance is below ratio times the second-best distance"
                  },
                  "min_inliers": {
                    "type": "integer",
                    "description": "Fewest RANSAC inliers for found to be true, 4-200 (default 10)"
                  },
                  "reproj_threshold": {
                    "type": "number",
                    "description": "RANSAC reprojection error in pixels below which a match is an inlier, 0.5-20 (default 3)"
                  }
                },
                "required": [
                  "image",
                  "template"
                ]
              },
              "example": {
                "image": "iVBORw0KGgoAAAANSUhEUgAAAIAAAABgCAAAAADwESWVAAANaklEQVRo3r1aeWwbVRr/ZsZ2fMVHYieOm3rSw0lLm6aFHnSLSlNoxdKuthQVhKACFioES6Ut1Wb/2kNod9EWsUh0BYhSbQEBWsqCWJoiUWiXttAWWtID0itp4hxNnMuxYyc+Z/bNZc+MZ8bOwT7HM29m3sz3m993vudgrcC2H7kdLIKptQPo+1j2aK/88nWh84r8Cg4z0qTyJ9OmDOD9mZE/ZQDvixEcmAZ3M6QCKQF5JgB+1ft0U1bAQ+oK2KluhJL255lhYBoGMCMApid/+gAOTPN+3ZQCkMQEFAgQG0EPszH9ZAyoKGDn/0sFCvK3TQ6BblpOKJO/Lbc9mO+KMxoHQF0+3z/IcLAXbX43SQB3n75dfuqLohxgm1wTB4tShMwG+vpOw+kpReBteZe2TcEI+9SCppIJHNCWn3euuVgbuH1GI+ApZnPCYLVYG49sKAigqjgK8uUr073tINxexbSG75mjYZaGTZoMMAje2V6EBg4UVHcbOcux1/sSgbqDF9GmFsp4TWyaKTdUVUDfPL+PJEvTHdxh7EoaoNxHV0Z5Y9ikAaAICvxIS2oGcJMkyYjNsWA2c0DrU8wu3R0EwPwOqBK0K0aQx8D2dwogOIsgnF38g1x+G8k25FXnRiDGnupn5UOUKbwXVkMOgLYKOAS7XxKfe+ZVUXHDlleL4exy4cxGsoH0kaX8UQjxzQEwxNndCQqgeg7qlH+7Mp8CRRs4D7vRB1gMtUg8+wfwqlBe+QUqfoPe2UdKCmQYjoB5MdvTs9vTSQAbyebjqiIYSLuGtu9mOnFCz7BQK+bheWbLOPMheMVH1vjIjxWSqRnd2+9FwidYm7sxRINuFifaowlg9Ic7LpXWxG45ztrPzaDXIxWP2h+AgbAlUeJ67mOrmo2gd7VO9JTZQWdNoKd2Ij04uXKHqOnNH44xFvIGIzKRso4ZDZkRN3iBaMuA3QOfyga3zKlBlPej6dWLZWry46fSUGkEpxv1O9JwphtxsoFTRunQYVjLD9skZ4AK0ZCkUkYjgP1Hn8NjQT48fxd/8WU45fVWeb2Pu8xoPMZ4uioAI5HGkNUlWCtMX0HydQ28kCT5+Ua5/CwAvDxiNAyVQwYmhv0WkBE89IqZ3Y9QDoCK8uGaEnU3Xdoxjl6Y9UBHsBNofHYFxonyGEilbMg7J53B0wTNxC2HhTsjUsAYJx8sSD68HYFl89UB2CqNiIFUO3LFeGcknjItYBWA28v04FMwwusIQSMci8eoMA0jNhx0MZpFfFkc4KIcJex7xVJM2lZt4xGkAjqK24yZttZwv30d9z46F/KYmqCaFzQeM4yWTVD3wlGwh1tvwWhAZHBAmLbmJusPOKP5G2GQAuCHRWxs2IvR8ZQ+FexOndQvPTo+mvEZEnR5otLACvIF5SaQtYHGL81AoErgZ82YfazVNpoCu/1iQ3ZY2BIDzKRnVH/tOjhFpdaHbfcuMMDoV6Gxe6hQsH/Q6O8DfaidcEG4ZXbIgA99bXQtv9G+nFEekN+px4G7jrEhxugCzAb1AJfOwwO5YYOOUizowvlwFqKzFy62DL1920OJC1cy9Ico9nYnqauj/oqB1Cw7RfXay0yxsKFy8DNkvvULGQAn18oIEAWiRmQ68JVwdEmKs1Ovh9kc1eWocM3ddWoIxvqS2OexTCJicbsrjaZ4O04D5aQoo3ncZYIQshucAmMlG4pIuXxZKObl17P5QNwCwPk/srEXUYC0ZS/MD/ZCW9NzUeeKmpFPBteXOZ3/GfBXl3237mQMMyUIS1moqtF7dsDp5wIH+S7aoO97igC+ynUvwW/53MDtavuFOG52RMU2eNf85guZib+Gl6xxjIYOr7JDomTWlpKWU2METekdj8zS/wNhWmcQhpMBjWSUlV+v4FyBbCLx9OhSogvkM5+cGaaJG9/Eui5vQnCH0zY7uK1H9JDCbSSW0Qc+tdfdmh2tlQ0b/dlCdvVq6JABWCVwE4SF90miZF1HNKFrbTcY3S2uNfjEjbsp3OP9sax0YtwaP/hNuNpM5tKwTwuAX1xIy1uX0OntBiGajA0OoU8EZT99mi7R6RpCLQ3mxE1UFVFO3UBv3EcFV67xmsWP8Qy6i5kbrs4/1Sl0aldcegSFnt7LSLjgjTo8igORCRsGLXB1EXLW6zcrxnU/rzuXrJMXDOR4QQCKBEAgQ3CduU9+Nhf5w83j4lCIO6KZDHWpcjUB1HIUtcudYfOiReWb859DXi6CgdVKOa5znnDHL5itjMkS00iMmIiZl7nu5yzzX+YGh9LagwYAvxYByAgEADQKykMlLozOJgImQJTZiDEarr25nq07MXhQ5TFSN3jt6RwAvyYBXCjiSp4uynt9jss1wAYmjEtFNCpkjKE03fHR1QcNWpMK3+WFWensV1eMC4gB0LGRUOJyb4B5eV44TwJWBnhf6MwPux0aEGy+90Tyc9NzPxQgQABAdR862daW8CyuwzBOLGSTNqzagkqG0d+3alFASuUD7gc/alCIAAhEuCLWsZLcuHleucsDNGsFuQ3KmbNqGV/pGQHRSWUAr+VKMn9hF3gdXn/9IkcBZqszpEeJ9gt8dQqsMfIkDLl331UBcHg/E0YHopnCVih3w1NKy9w4gwC5AZcixtoG+lKUdbzGGOcL+9zgyJDr/pozFzJtf9u+GCZiVncRAHCVGCBaT6EkRhCdsHnuW7N0jVPp6YMAt91/L2L/7UMBC51KKwFYI9GAFICKBVBiAFUrVlZ7XWQGXAojh9C38pdPoeRz/PC3yGFT+UMINh89zWy25qlg9anVigtKFINT8EOiymbw6TFQYQC1W13HT0DH0AIUM7D8SFvD7bZy34/wQgrgIVDUkX6eM2slGDDQAAA+FDXxhWYDDIYVQhGzCW7lj7YqrhU3a8dCrimqIMmXNM+CbbMHRcekshUGp7RG1LVKclhuz3+9xOAsdm+t/wvCZ8XCqQyOabsBrkLApoIMaOmA48dog3QgIR/i2SAmIAtgz55C8nM1iZYOJEd6tx4SaUUjkKmAkb6nSUn+r0QqEGqSYhjgWulEaiReqewGOQD8uzdpGSDT6gJz1RjATHF2NiljgFkmolMpvcwIJDNUnVR83txRYgRSAG5MSDd6HDfhCcbiB8dKJWMsVDjZXS1Nz77KfBtoaipkAJLKmGu5UF9iwHDAcQUdGJxYni+SS2UqaMpzAObXls1FWOGAEKYY49BbTG63yyvPNa5IIiU1HpvEEXVNKg54qHg/NOoYXeh3mJVoK00lRuPSBULfsUaVQNRcIBJFbHlWaHe73BX9TI2eiigCACtEPRpukBcJqy+oAljWtViqzI0udzmkaZSZjImq+TbluwxOoywYkmkRBcSvZQoISrnuF9/plC5cGn0uM9ATExmipjrqq7MrLxkN9/Vc0UmuUSHo7JzDrwDqCkZgdTdgavTxDI2m8Lb0EggTTum1VCQSjkTGWGXNltjAzl0Ax+D8rpclKmgunI7kbgDpOB9o7RNj0VQOABKMWi4IjwmdgQBqXbuE9c88G9AmIM8N6Ljg4gR6TqKvXIg4J8akA1HejCLBnV2Pg33JEmG2d14CoLACAGb3S+05lZvqllQM0gNGAYBdDIAOhUa/7Ql8fxXN2v65VPyjgBiAknxKlKwxC7P43iUFIIovGKFLQTwbawTqR0NI+lmtl9Jl5Z9BH8nTjRQQJciNSodtmZjOe43RwUrpEEJU+iMA0ZEyAUAixMiWVLl1VwEeb8kdPykkoyZlaCUokzsTgBv1uDXCejKOyYwgSonjYqZ3PI6m5BRS9rXW0EWFdLrzWViWRcD/4oM9xiWDZtn7A26KoYeOG9mKxtJQ/+buzuaNf5T+Jp+Mx0WADddGglRfZ9dJNbZ3AjwLJy0S+Vkb2CQHwOVaDExJgkg9g4Xh3Jn7vAFKUsIZMgKAWE/vzWDbf4uoLO9A+CzLpTawp0nrDkpH677Ek+mj9Ve8b3TOlVsQ1dPbi/7+vQTm7tB6zKNv5frLJdlwjzICCkMczG2t6kVTAvrSPANm6Z4L1itiAP1dnVd7e79h+zfgBYAdsE9FOo9g71WoOyn3AhUENG1IQp/D5bhcP5CshiRW29Z+p4e3wkgXiiqBewAcjoOFWX+U3b7FLLHXqbkhQvA818smw9iFGB0uB9oLRisyBgz3tx/a0plhAlqg6xEwLWTXWv4kDH+B3e7YpyY+e/zE/rxfzfaIi0JRNs7AQMc8caxeD7cZvzD+XXRmt9C5wSHYpyF+J/9fbvvhTllNqGaDBGGok9UL5742YcXPpeBRVv5b3Ovv5f/L7on83w1ZDpryGAAYlj5vPbt9SZkB5AX7tMnPtrb8qhiy04NptH3qb6/ecJhBBJMXL60HtAPSpMSrka8CACWIDUfY/bLJiFkxffEcADZBMQiObGjRnrjnyefWzNdOWTwHYJkIgSgWF0LwXZYBFkb1VMQLbgjZSXoOAaONo4XcUK6F/UWJb9OYmByZnCGuzTHAx9knmMO12nfNV2FAGpOhGAaygQgehqcUoE1OBZKIOOn2MPuL5PHJIuAAPCAuFXJF7AeTA/AuiKxycgw8AIoIPoCfvv0PJrSWN9Vip0UAAAAASUVORK5CYII=",
                "template": "iVBORw0KGgoAAAANSUhEUgAAAEAAAAAwCAAAAACEICPDAAADAklEQVRIx61UT0gUURz+Znfazdyx0Ex3U1smVqJCKwn6c5FCCaKDoYdOEh7WywQiQh6UisKgS7QgLLSXQrpIdPTPISIiiAqlSHJptbINRTR1E1m3fc0b58/OOjM7rv6YefPmzft9v+/73pvHPIUUftq0ARGYxSjQIHWiysggbRzyyzS2HFJ+twLgzzV9VOlEM/Obo46MOZYKoCjQ5YsS/PYI0Jg0yBc98PvptUHAUsEhCSGqz5dM1MpHctMI6PPhsGl5A0oN+OsA9BYGg1kIJvlmDILShVAoJA+MqW1Alx9grXjfS8Px0Iklgmb3shvJmaqkC31YZV3N6hzmtfEmoPXDV4uc6yvVB98TYKWmdOGL1/2r5zmZiVfe0Cw1YxCWRNytQM9ExWlg+WMxPlV7gZ6TX9NcfcaKqACRtsgmhLT4vPhdENt2rzORLge45JrPM/02DiEa2JjH6vdAr4ZQNgt0uP+tdYj9xflHvg/fLg0nnGyyyEO/hjAk5NoHZcAel/f8C7E7XOsDQ5AACDzK95AeYPEVxqfoBCkIkTrsrr/BqVmkhi4DvoUBYJX0CsLhswKtLugkpH78SU3UyekgjAjBUBHk5e4SvCk8BZS74pUkfq4gLUbKKSiFZYDV/jXHZOJnnSaAofcC8OQWi5Er4kvfkegYCvbh+hLeDTS1btoHgzWB+zeZXsKoHGjM0vXYGOkTV6WppL/Lo3dK9oAk57l5bh2qCYxqJOS/ohtoOVp2OytfYfB5eGnveqqg5TGRUhUeeg6GITM43l7ceeFMZ5VSmqhUwhoHKwCgHvuPZThIMkhYIigAhSfAezXtDKPmh61PGhsnkrUIO0eaghDLF0BGiBki2DtUJQQ+bwmailjeANtaBYVCmDeiwMI+wtYYcAZjvH0AjqOXQcS2ZyJvlwFnqmIThSwT78jPB7TpyncZ5yw1xHIs45x0t/4eaazNayOp1Rtt2ugwyRcPl3GTmrHt/Qt8FglTAFMKvJWJJv4/079eM2dwYCd/51pzG3f0QPkPRu/dDgU3nB4AAAAASUVORK5CYII=",
                "detector": "sift"
              }
            }
          }
        }
      }
    }
  },
  "components": {
    "securitySchemes": {
      "apiKey": {
        "type": "http",
        "scheme": "bearer",
        "description": "An API key with prepaid credits, from https://visionflow-match.saastemly.com"
      }
    }
  },
  "x-mcp-server": "https://visionflow-match.saastemly.com/mcp"
}