{
  "openapi": "3.1.1",
  "info": {
    "title": "Cancellation Navigator API",
    "version": "1.0.0",
    "summary": "Verified steps to cancel Netflix, Spotify, Prime & more, plus a cancellation letter.",
    "description": "Every endpoint performs the same calculation as the human page and returns inputs, result, units, assumptions, sources, warnings and computedAt. MCP endpoint: /mcp."
  },
  "servers": [
    {
      "url": "https://cancellationnavigator.usefulweb.site"
    }
  ],
  "paths": {
    "/api/v1/calculate": {
      "post": {
        "operationId": "calculate",
        "summary": "Verified steps to cancel Netflix, Spotify, Prime & more, plus a cancellation letter.",
        "description": "Choose a subscription and how you signed up. Cancellation Navigator shows the steps from the official help page (with the date we last checked it), what to do if you are billed through the App Store, Google Play or a carrier, your German online cancellation-button rights (§ 312k BGB), a ready-to-send cancellation letter and a proof-keeping checklist.\n\nMethodology:\n- Service steps were condensed from each service's official help page on the date shown (verifiedAt); nothing is added that the page does not say. If a page could not be read reliably, only the official link is given (steps not verified).\n- App Store and Google Play subscriptions are billed by Apple/Google, so the store's own cancellation steps (Apple Support, Google Play Help) are shown first for those channels.\n- Carrier/partner billing: cancel with the company that bills you (e.g. Spotify's help states partner plans are cancelled with the partner).\n- Germany: § 312k BGB (Kündigungsbutton) summary from gesetze-im-internet.de. Rights for other countries are not asserted because they were not verified.\n- Unknown services get a generic method and letter, clearly marked as unverified.\n\nNot legal advice. Service flows change; the official page linked is authoritative.",
        "tags": [
          "everyday"
        ],
        "x-mcp-tool": "cancellation_navigator",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/CancellationNavigatorInput"
              },
              "examples": {
                "example1": {
                  "summary": "Netflix signed up on the web, Germany",
                  "value": {
                    "service": "netflix",
                    "country": "DE",
                    "channel": "web"
                  }
                },
                "example2": {
                  "summary": "ChatGPT Plus bought in the iPhone app, US",
                  "value": {
                    "service": "chatgpt-plus",
                    "country": "US",
                    "channel": "app-store"
                  }
                },
                "example3": {
                  "summary": "Unknown local gym, Germany",
                  "value": {
                    "service": "other",
                    "serviceName": "FitClub Musterstadt",
                    "country": "DE",
                    "channel": "other",
                    "yourName": "Max Mustermann"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Calculation result envelope.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/CancellationNavigatorResult"
                }
              }
            }
          },
          "400": {
            "description": "Malformed JSON body.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "$ref": "#/components/schemas/Problem"
                }
              }
            }
          },
          "422": {
            "description": "Invalid input (see errors[]).",
            "content": {
              "application/problem+json": {
                "schema": {
                  "$ref": "#/components/schemas/Problem"
                }
              }
            }
          },
          "429": {
            "description": "Rate limit exceeded (see Retry-After).",
            "content": {
              "application/problem+json": {
                "schema": {
                  "$ref": "#/components/schemas/Problem"
                }
              }
            }
          }
        }
      }
    },
    "/api/v1/tool": {
      "get": {
        "operationId": "getToolDefinition",
        "summary": "Inputs, output schema and examples for this tool",
        "responses": {
          "200": {
            "description": "Tool definition.",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          }
        }
      }
    }
  },
  "components": {
    "schemas": {
      "Problem": {
        "type": "object",
        "description": "RFC 9457 problem details. 422 responses include per-field `errors`.",
        "required": [
          "type",
          "title",
          "status",
          "detail"
        ],
        "properties": {
          "type": {
            "type": "string"
          },
          "title": {
            "type": "string"
          },
          "status": {
            "type": "integer"
          },
          "detail": {
            "type": "string"
          },
          "code": {
            "type": "string"
          },
          "errors": {
            "type": "array",
            "items": {
              "type": "object",
              "required": [
                "field",
                "message"
              ],
              "properties": {
                "field": {
                  "type": "string"
                },
                "message": {
                  "type": "string"
                }
              }
            }
          }
        }
      },
      "CancellationNavigatorInput": {
        "type": "object",
        "additionalProperties": false,
        "properties": {
          "service": {
            "title": "Service",
            "type": "string",
            "enum": [
              "netflix",
              "spotify",
              "amazon-prime",
              "kindle-unlimited",
              "disney-plus",
              "hulu",
              "paramount-plus",
              "youtube-premium",
              "google-one",
              "microsoft-365",
              "xbox",
              "playstation-plus",
              "adobe",
              "audible",
              "dazn",
              "linkedin-premium",
              "dropbox",
              "chatgpt-plus",
              "duolingo",
              "other"
            ],
            "default": "netflix"
          },
          "serviceName": {
            "title": "Service name (if Other)",
            "type": "string",
            "maxLength": 120
          },
          "country": {
            "title": "Your country",
            "type": "string",
            "enum": [
              "DE",
              "AT",
              "EU-other",
              "UK",
              "US",
              "other"
            ],
            "default": "DE"
          },
          "channel": {
            "title": "Where did you sign up / who bills you?",
            "type": "string",
            "enum": [
              "web",
              "app-store",
              "google-play",
              "carrier",
              "other"
            ],
            "default": "web"
          },
          "yourName": {
            "title": "Your name (for the letter, optional)",
            "type": "string",
            "maxLength": 120
          },
          "customerNumber": {
            "title": "Customer / account number (optional)",
            "type": "string",
            "maxLength": 80
          }
        },
        "required": []
      },
      "CancellationNavigatorResult": {
        "type": "object",
        "additionalProperties": false,
        "required": [
          "schemaVersion",
          "tool",
          "computedAt",
          "inputs",
          "summary",
          "result",
          "units",
          "assumptions",
          "sources",
          "warnings",
          "presentation",
          "links"
        ],
        "properties": {
          "schemaVersion": {
            "type": "string",
            "const": "1.0"
          },
          "tool": {
            "type": "object",
            "additionalProperties": false,
            "required": [
              "id",
              "name",
              "version"
            ],
            "properties": {
              "id": {
                "type": "string"
              },
              "name": {
                "type": "string"
              },
              "version": {
                "type": "string"
              }
            }
          },
          "computedAt": {
            "type": "string",
            "format": "date-time"
          },
          "inputs": {
            "type": "object",
            "description": "Normalised inputs actually used, including applied defaults."
          },
          "summary": {
            "type": "string"
          },
          "result": {
            "type": "object",
            "additionalProperties": false,
            "required": [
              "service",
              "verified",
              "officialUrl",
              "verifiedAt",
              "stepsSource",
              "steps",
              "serviceNotes",
              "channelNotes",
              "rights",
              "letter"
            ],
            "properties": {
              "service": {
                "type": "string"
              },
              "verified": {
                "type": "boolean",
                "description": "True if the steps come from an official help page checked on verifiedAt (false = generic method)."
              },
              "officialUrl": {
                "type": [
                  "string",
                  "null"
                ],
                "format": "uri"
              },
              "verifiedAt": {
                "type": [
                  "string",
                  "null"
                ],
                "format": "date"
              },
              "stepsSource": {
                "type": "string",
                "enum": [
                  "service-help-page",
                  "apple-support",
                  "google-play-help",
                  "generic"
                ]
              },
              "steps": {
                "type": "array",
                "items": {
                  "type": "string"
                }
              },
              "serviceNotes": {
                "type": "array",
                "items": {
                  "type": "string"
                }
              },
              "channelNotes": {
                "type": "array",
                "items": {
                  "type": "string"
                }
              },
              "rights": {
                "type": "array",
                "items": {
                  "type": "object",
                  "additionalProperties": false,
                  "required": [
                    "title",
                    "url",
                    "text"
                  ],
                  "properties": {
                    "title": {
                      "type": "string"
                    },
                    "url": {
                      "type": [
                        "string",
                        "null"
                      ]
                    },
                    "text": {
                      "type": "string"
                    }
                  }
                }
              },
              "letter": {
                "type": "string",
                "description": "Plain-text cancellation letter template."
              }
            }
          },
          "units": {
            "type": "object",
            "additionalProperties": {
              "type": "string"
            }
          },
          "assumptions": {
            "type": "array",
            "items": {
              "type": "string"
            }
          },
          "sources": {
            "type": "array",
            "items": {
              "type": "object",
              "additionalProperties": false,
              "required": [
                "title"
              ],
              "properties": {
                "title": {
                  "type": "string"
                },
                "url": {
                  "type": "string"
                },
                "publisher": {
                  "type": "string"
                },
                "retrievedAt": {
                  "type": "string"
                },
                "note": {
                  "type": "string"
                }
              }
            }
          },
          "warnings": {
            "type": "array",
            "items": {
              "type": "string"
            }
          },
          "presentation": {
            "type": "array",
            "items": {
              "type": "object"
            },
            "description": "Display blocks used by the human page (same data)."
          },
          "links": {
            "type": "object",
            "additionalProperties": false,
            "required": [
              "human",
              "api",
              "openapi",
              "methodology"
            ],
            "properties": {
              "human": {
                "type": "string",
                "format": "uri"
              },
              "api": {
                "type": "string",
                "format": "uri"
              },
              "openapi": {
                "type": "string",
                "format": "uri"
              },
              "methodology": {
                "type": "string",
                "format": "uri"
              }
            }
          }
        }
      }
    }
  }
}