Cancel Subscription
curl --request DELETE \
--url https://api.nozle.app/engine/api/v1/subscriptions/{id} \
--header 'Authorization: Bearer <token>'import requests
url = "https://api.nozle.app/engine/api/v1/subscriptions/{id}"
headers = {"Authorization": "Bearer <token>"}
response = requests.delete(url, headers=headers)
print(response.text)const options = {method: 'DELETE', headers: {Authorization: 'Bearer <token>'}};
fetch('https://api.nozle.app/engine/api/v1/subscriptions/{id}', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));package main
import (
"fmt"
"net/http"
"io"
)
func main() {
url := "https://api.nozle.app/engine/api/v1/subscriptions/{id}"
req, _ := http.NewRequest("DELETE", url, nil)
req.Header.Add("Authorization", "Bearer <token>")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}require 'uri'
require 'net/http'
url = URI("https://api.nozle.app/engine/api/v1/subscriptions/{id}")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Delete.new(url)
request["Authorization"] = 'Bearer <token>'
response = http.request(request)
puts response.read_body<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://api.nozle.app/engine/api/v1/subscriptions/{id}",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "DELETE",
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}HttpResponse<String> response = Unirest.delete("https://api.nozle.app/engine/api/v1/subscriptions/{id}")
.header("Authorization", "Bearer <token>")
.asString();Checkout & Subscriptions
Cancel Subscription
DELETE
/
engine
/
api
/
v1
/
subscriptions
/
{id}
Cancel Subscription
curl --request DELETE \
--url https://api.nozle.app/engine/api/v1/subscriptions/{id} \
--header 'Authorization: Bearer <token>'import requests
url = "https://api.nozle.app/engine/api/v1/subscriptions/{id}"
headers = {"Authorization": "Bearer <token>"}
response = requests.delete(url, headers=headers)
print(response.text)const options = {method: 'DELETE', headers: {Authorization: 'Bearer <token>'}};
fetch('https://api.nozle.app/engine/api/v1/subscriptions/{id}', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));package main
import (
"fmt"
"net/http"
"io"
)
func main() {
url := "https://api.nozle.app/engine/api/v1/subscriptions/{id}"
req, _ := http.NewRequest("DELETE", url, nil)
req.Header.Add("Authorization", "Bearer <token>")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}require 'uri'
require 'net/http'
url = URI("https://api.nozle.app/engine/api/v1/subscriptions/{id}")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Delete.new(url)
request["Authorization"] = 'Bearer <token>'
response = http.request(request)
puts response.read_body<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://api.nozle.app/engine/api/v1/subscriptions/{id}",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "DELETE",
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}HttpResponse<String> response = Unirest.delete("https://api.nozle.app/engine/api/v1/subscriptions/{id}")
.header("Authorization", "Bearer <token>")
.asString();Base URL:
For customer-facing Cancel/Keep with a confirmed ending date, use the transition preview/apply flow. It supports the atomic
https://api.nozle.app/engine/api/v1.
Cancel a subscription immediately or schedule cancellation for the next renewal boundary.
Use this endpoint only from an authenticated merchant backend. Derive the customer from the logged-in user or team; never accept an authoritative customer_id from browser input.
Auth: secret key only. Publishable keys are always rejected.
string
required
The external subscription ID to cancel, not the Core internal UUID.
string
required
External customer ID derived by the trusted merchant backend. The subscription must belong to that customer and organization.
string
default:"immediate"
end_of_period keeps the subscription active until its next renewal boundary. immediate terminates it now. The raw HTTP API defaults to immediate for backward compatibility; the Node.js, Python, and Go SDK methods default to end_of_period.expected_effective_at guard and the uncancel operation.
Response
Forend_of_period, the subscription remains active and ending_at contains the next renewal boundary. An open paid upgrade checkout of the subscription is canceled, and its Stripe Checkout Session or Razorpay order is expired. Engine access checks deny access at that boundary; the termination worker updates the subscription row according to its schedule and handles renewal termination. Repeating the request does not extend an earlier scheduled ending.
For immediate, the response contains the terminated subscription.
curl --request DELETE \
'https://api.nozle.app/engine/api/v1/subscriptions/sub_123?customer_id=cust_123&cancellation_policy=end_of_period' \
--header 'Authorization: Bearer sk_nozle_...'