curl --request POST \
--url https://api.gojinko.com/v1/best_price_guarantee \
--header 'Content-Type: application/json' \
--header 'X-API-Key: <api-key>' \
--data '
{
"product": "hotel",
"trip_item_token": "htl_8f3c1d5e9a7b2c40",
"reference": {
"url": "https://www.booking.com/hotel/fr/example.html?checkin=2026-11-10",
"total": "412.50",
"currency": "USD",
"screenshot_url": "https://files.example.com/screenshots/8f3.png"
},
"objective": "price_parity",
"wait_seconds": 15
}
'import requests
url = "https://api.gojinko.com/v1/best_price_guarantee"
payload = {
"product": "hotel",
"trip_item_token": "htl_8f3c1d5e9a7b2c40",
"reference": {
"url": "https://www.booking.com/hotel/fr/example.html?checkin=2026-11-10",
"total": "412.50",
"currency": "USD",
"screenshot_url": "https://files.example.com/screenshots/8f3.png"
},
"objective": "price_parity",
"wait_seconds": 15
}
headers = {
"X-API-Key": "<api-key>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {'X-API-Key': '<api-key>', 'Content-Type': 'application/json'},
body: JSON.stringify({
product: 'hotel',
trip_item_token: 'htl_8f3c1d5e9a7b2c40',
reference: {
url: 'https://www.booking.com/hotel/fr/example.html?checkin=2026-11-10',
total: '412.50',
currency: 'USD',
screenshot_url: 'https://files.example.com/screenshots/8f3.png'
},
objective: 'price_parity',
wait_seconds: 15
})
};
fetch('https://api.gojinko.com/v1/best_price_guarantee', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://api.gojinko.com/v1/best_price_guarantee",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => json_encode([
'product' => 'hotel',
'trip_item_token' => 'htl_8f3c1d5e9a7b2c40',
'reference' => [
'url' => 'https://www.booking.com/hotel/fr/example.html?checkin=2026-11-10',
'total' => '412.50',
'currency' => 'USD',
'screenshot_url' => 'https://files.example.com/screenshots/8f3.png'
],
'objective' => 'price_parity',
'wait_seconds' => 15
]),
CURLOPT_HTTPHEADER => [
"Content-Type: application/json",
"X-API-Key: <api-key>"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://api.gojinko.com/v1/best_price_guarantee"
payload := strings.NewReader("{\n \"product\": \"hotel\",\n \"trip_item_token\": \"htl_8f3c1d5e9a7b2c40\",\n \"reference\": {\n \"url\": \"https://www.booking.com/hotel/fr/example.html?checkin=2026-11-10\",\n \"total\": \"412.50\",\n \"currency\": \"USD\",\n \"screenshot_url\": \"https://files.example.com/screenshots/8f3.png\"\n },\n \"objective\": \"price_parity\",\n \"wait_seconds\": 15\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("X-API-Key", "<api-key>")
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.post("https://api.gojinko.com/v1/best_price_guarantee")
.header("X-API-Key", "<api-key>")
.header("Content-Type", "application/json")
.body("{\n \"product\": \"hotel\",\n \"trip_item_token\": \"htl_8f3c1d5e9a7b2c40\",\n \"reference\": {\n \"url\": \"https://www.booking.com/hotel/fr/example.html?checkin=2026-11-10\",\n \"total\": \"412.50\",\n \"currency\": \"USD\",\n \"screenshot_url\": \"https://files.example.com/screenshots/8f3.png\"\n },\n \"objective\": \"price_parity\",\n \"wait_seconds\": 15\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://api.gojinko.com/v1/best_price_guarantee")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["X-API-Key"] = '<api-key>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"product\": \"hotel\",\n \"trip_item_token\": \"htl_8f3c1d5e9a7b2c40\",\n \"reference\": {\n \"url\": \"https://www.booking.com/hotel/fr/example.html?checkin=2026-11-10\",\n \"total\": \"412.50\",\n \"currency\": \"USD\",\n \"screenshot_url\": \"https://files.example.com/screenshots/8f3.png\"\n },\n \"objective\": \"price_parity\",\n \"wait_seconds\": 15\n}"
response = http.request(request)
puts response.read_body{
"id": "ngo_mfrggzdfmztwq2lknnwg23tpob",
"status": "offered",
"offer": {
"trip_item_token": "htl_neg_ogydqmrsgaydamjqgezdgnbvgy",
"offer_id": "htl_neg_ogydqmrsgaydamjqgezdgnbvgy",
"price_money": {
"value": 41250,
"currency": "USD",
"decimal_places": 2,
"display": "USD 412.50"
},
"original": {
"kind": "offer",
"trip_item_token": "htl_8f3c1d5e9a7b2c40",
"offer_id": "htl_8f3c1d5e9a7b2c40",
"total_money": {
"value": 43780,
"currency": "USD",
"decimal_places": 2,
"display": "USD 437.80"
}
},
"reference": {
"total_money": {
"value": 41250,
"currency": "USD",
"decimal_places": 2,
"display": "USD 412.50"
},
"verified": true
},
"saving_money": {
"value": 2530,
"currency": "USD",
"decimal_places": 2,
"display": "USD 25.30"
},
"expires_at": "2026-10-12T10:30:00Z"
}
}{
"error": {
"code": "BAD_REQUEST",
"message": "Malformed JSON in request body.",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}{
"error": {
"code": "AUTH_REQUIRED",
"message": "Invalid or expired API key.",
"doc_url": "https://docs.gojinko.com/authentication/api-keys"
}
}{
"error": {
"code": "PAYMENT_REQUIRED",
"message": "Insufficient balance — this call costs $0.0150 and your organization has $0.0000 available. Top up at https://dashboard.gojinko.com/developers/billing/topup",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}{
"error": {
"code": "NOT_FOUND",
"message": "Resource not found.",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}{
"error": {
"code": "CONFLICT",
"message": "The operation conflicts with the current state of the resource.",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}{
"error": {
"code": "GONE",
"message": "The resource no longer exists.",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}{
"error": {
"code": "BAD_REQUEST",
"message": "A required field is missing or invalid.",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}{
"error": {
"code": "RATE_LIMITED",
"message": "Too many requests. Retry after the Retry-After delay.",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}{
"error": {
"code": "UPSTREAM_REJECTED",
"message": "The request was declined for this offer. Try another offer.",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}{
"error": {
"code": "UPSTREAM_UNAVAILABLE",
"message": "The service is temporarily unavailable. Retry after the Retry-After delay.",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}{
"error": {
"code": "UPSTREAM_TIMEOUT",
"message": "The request timed out before a result was available. Retry the request.",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}best-price-guarantee
Best Price Guarantee: ask for a hotel offer at a lower price found elsewhere
curl --request POST \
--url https://api.gojinko.com/v1/best_price_guarantee \
--header 'Content-Type: application/json' \
--header 'X-API-Key: <api-key>' \
--data '
{
"product": "hotel",
"trip_item_token": "htl_8f3c1d5e9a7b2c40",
"reference": {
"url": "https://www.booking.com/hotel/fr/example.html?checkin=2026-11-10",
"total": "412.50",
"currency": "USD",
"screenshot_url": "https://files.example.com/screenshots/8f3.png"
},
"objective": "price_parity",
"wait_seconds": 15
}
'import requests
url = "https://api.gojinko.com/v1/best_price_guarantee"
payload = {
"product": "hotel",
"trip_item_token": "htl_8f3c1d5e9a7b2c40",
"reference": {
"url": "https://www.booking.com/hotel/fr/example.html?checkin=2026-11-10",
"total": "412.50",
"currency": "USD",
"screenshot_url": "https://files.example.com/screenshots/8f3.png"
},
"objective": "price_parity",
"wait_seconds": 15
}
headers = {
"X-API-Key": "<api-key>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {'X-API-Key': '<api-key>', 'Content-Type': 'application/json'},
body: JSON.stringify({
product: 'hotel',
trip_item_token: 'htl_8f3c1d5e9a7b2c40',
reference: {
url: 'https://www.booking.com/hotel/fr/example.html?checkin=2026-11-10',
total: '412.50',
currency: 'USD',
screenshot_url: 'https://files.example.com/screenshots/8f3.png'
},
objective: 'price_parity',
wait_seconds: 15
})
};
fetch('https://api.gojinko.com/v1/best_price_guarantee', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://api.gojinko.com/v1/best_price_guarantee",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => json_encode([
'product' => 'hotel',
'trip_item_token' => 'htl_8f3c1d5e9a7b2c40',
'reference' => [
'url' => 'https://www.booking.com/hotel/fr/example.html?checkin=2026-11-10',
'total' => '412.50',
'currency' => 'USD',
'screenshot_url' => 'https://files.example.com/screenshots/8f3.png'
],
'objective' => 'price_parity',
'wait_seconds' => 15
]),
CURLOPT_HTTPHEADER => [
"Content-Type: application/json",
"X-API-Key: <api-key>"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://api.gojinko.com/v1/best_price_guarantee"
payload := strings.NewReader("{\n \"product\": \"hotel\",\n \"trip_item_token\": \"htl_8f3c1d5e9a7b2c40\",\n \"reference\": {\n \"url\": \"https://www.booking.com/hotel/fr/example.html?checkin=2026-11-10\",\n \"total\": \"412.50\",\n \"currency\": \"USD\",\n \"screenshot_url\": \"https://files.example.com/screenshots/8f3.png\"\n },\n \"objective\": \"price_parity\",\n \"wait_seconds\": 15\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("X-API-Key", "<api-key>")
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.post("https://api.gojinko.com/v1/best_price_guarantee")
.header("X-API-Key", "<api-key>")
.header("Content-Type", "application/json")
.body("{\n \"product\": \"hotel\",\n \"trip_item_token\": \"htl_8f3c1d5e9a7b2c40\",\n \"reference\": {\n \"url\": \"https://www.booking.com/hotel/fr/example.html?checkin=2026-11-10\",\n \"total\": \"412.50\",\n \"currency\": \"USD\",\n \"screenshot_url\": \"https://files.example.com/screenshots/8f3.png\"\n },\n \"objective\": \"price_parity\",\n \"wait_seconds\": 15\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://api.gojinko.com/v1/best_price_guarantee")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["X-API-Key"] = '<api-key>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"product\": \"hotel\",\n \"trip_item_token\": \"htl_8f3c1d5e9a7b2c40\",\n \"reference\": {\n \"url\": \"https://www.booking.com/hotel/fr/example.html?checkin=2026-11-10\",\n \"total\": \"412.50\",\n \"currency\": \"USD\",\n \"screenshot_url\": \"https://files.example.com/screenshots/8f3.png\"\n },\n \"objective\": \"price_parity\",\n \"wait_seconds\": 15\n}"
response = http.request(request)
puts response.read_body{
"id": "ngo_mfrggzdfmztwq2lknnwg23tpob",
"status": "offered",
"offer": {
"trip_item_token": "htl_neg_ogydqmrsgaydamjqgezdgnbvgy",
"offer_id": "htl_neg_ogydqmrsgaydamjqgezdgnbvgy",
"price_money": {
"value": 41250,
"currency": "USD",
"decimal_places": 2,
"display": "USD 412.50"
},
"original": {
"kind": "offer",
"trip_item_token": "htl_8f3c1d5e9a7b2c40",
"offer_id": "htl_8f3c1d5e9a7b2c40",
"total_money": {
"value": 43780,
"currency": "USD",
"decimal_places": 2,
"display": "USD 437.80"
}
},
"reference": {
"total_money": {
"value": 41250,
"currency": "USD",
"decimal_places": 2,
"display": "USD 412.50"
},
"verified": true
},
"saving_money": {
"value": 2530,
"currency": "USD",
"decimal_places": 2,
"display": "USD 25.30"
},
"expires_at": "2026-10-12T10:30:00Z"
}
}{
"error": {
"code": "BAD_REQUEST",
"message": "Malformed JSON in request body.",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}{
"error": {
"code": "AUTH_REQUIRED",
"message": "Invalid or expired API key.",
"doc_url": "https://docs.gojinko.com/authentication/api-keys"
}
}{
"error": {
"code": "PAYMENT_REQUIRED",
"message": "Insufficient balance — this call costs $0.0150 and your organization has $0.0000 available. Top up at https://dashboard.gojinko.com/developers/billing/topup",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}{
"error": {
"code": "NOT_FOUND",
"message": "Resource not found.",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}{
"error": {
"code": "CONFLICT",
"message": "The operation conflicts with the current state of the resource.",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}{
"error": {
"code": "GONE",
"message": "The resource no longer exists.",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}{
"error": {
"code": "BAD_REQUEST",
"message": "A required field is missing or invalid.",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}{
"error": {
"code": "RATE_LIMITED",
"message": "Too many requests. Retry after the Retry-After delay.",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}{
"error": {
"code": "UPSTREAM_REJECTED",
"message": "The request was declined for this offer. Try another offer.",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}{
"error": {
"code": "UPSTREAM_UNAVAILABLE",
"message": "The service is temporarily unavailable. Retry after the Retry-After delay.",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}{
"error": {
"code": "UPSTREAM_TIMEOUT",
"message": "The request timed out before a result was available. Retry the request.",
"doc_url": "https://docs.gojinko.com/concepts/errors"
}
}POST /v1/hotel_search with the lower price the traveller found for the same stay on another site: the link, a screenshot address and the total payable at booking, in the currency of the offer. The submission is reviewed in the background and this call answers pending with an id, or the result when wait_seconds let it finish in time. The answer carries the state of the request in status: pending while the review runs, then offered with the new offer, or declined with the reason. A decline is a 200: it is an answer, not a failure of the call. An offered result is a NEW offer id to add to a trip; the submitted offer is left as it was. Jinko enables Best Price Guarantee per account: a key it is not enabled for is answered HTTP 200 status: declined with decline.reason: feature_disabled.Authorizations
Body
The kind of product the request is about. Only hotel exists today.
hotel "hotel"
The hotel offer the traveller compared: hotels[].offers[].trip_item_token from POST /v1/hotel_search. It names the hotel, the dates, the party and the rate. An offer is kept for 75 minutes after the search that returned it.
1"htl_8f3c1d5e9a7b2c40"
Show child attributes
Show child attributes
What is asked for. price_parity (the default, and the only value today) asks for the reference price, nothing lower.
price_parity "price_parity"
How long this call waits for the result before answering, 0–20 seconds (default 0: answer at once). It only decides when the call returns; the review continues either way, and a call that waited without a result answers pending.
0 <= x <= 2015
Response
The state of the request
pending: the review is still running — read the request again; this is not a decline. It can take up to a few minutes when the reference page is checked. offered: offer holds the new offer. declined: no offer, see decline.reason. expired: an offer was made and not used before expires_at. Treat any other value as pending.
"offered"
Identifies the request; read its result with GET /v1/best_price_guarantee/{id}. Absent when the submission was declined before being recorded (feature_disabled, an unknown product).
"ngo_mfrggzdfmztwq2lknnwg23tpob"
Present while status is pending: a suggested pause before reading again.
2
Show child attributes
Show child attributes
Present when status is declined.
Show child attributes
Show child attributes
