UK Address Validator
Cleanse a full UK address and return a suggested Royal Mail PAF address.
Send the address in query; postcode and post_town are optional hints. Normally omit county. A candidate means an address was found, not that every part of the input was correct. Use address_complete and the quality fields to decide whether to accept it.
Completed live lookups are charged, including HTTP 404 no-match results. Invalid input, service failures and demo responses are not charged.
Send the address in query; postcode and post_town are optional hints. Normally omit county. A candidate means an address was found, not that every part of the input was correct. Use address_complete and the quality fields to decide whether to accept it.
Completed live lookups are charged, including HTTP 404 no-match results. Invalid input, service failures and demo responses are not charged.
Endpoint
POST
https://api.provero.io/api/validate/uk-address
Headers
Authorization: Bearer REPLACE_WITH_API_TOKEN
Content-Type: application/json
Accept: application/json
Request Body
| Field | Type | Required | Description |
|---|---|---|---|
query
|
string |
Yes | Free-form address to validate and standardise. |
postcode
|
string |
No | Optional UK postcode hint. Case and whitespace-only formatting errors are normalised before matching. Partial or otherwise impaired values may be used as review-only hints. |
post_town
|
string |
No | Optional post town hint. |
county
|
string |
No | Optional county hint. Normally omit this for UK addresses. |
Request Body example (JSON)
{
"query": "10 Downing Street, London, SW1A 2AA",
"postcode": "SW1A 2AA",
"post_town": "London"
}
Code Examples
import requests
url = "https://api.provero.io/api/validate/uk-address"
payload = {
"query": "10 Downing Street, London, SW1A 2AA",
"postcode": "SW1A 2AA",
"post_town": "London"
}
headers = {
"Authorization": "Bearer REPLACE_WITH_API_TOKEN",
"Content-Type": "application/json",
"Accept": "application/json"
}
response = requests.post(url, headers=headers, json=payload)
print(response.status_code)
print(response.json())
<?php
$payload = [
"query" => "10 Downing Street, London, SW1A 2AA",
"postcode" => "SW1A 2AA",
"post_town" => "London",
];
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://api.provero.io/api/validate/uk-address",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_POST => true,
CURLOPT_POSTFIELDS => json_encode($payload),
CURLOPT_HTTPHEADER => [
"Authorization: Bearer REPLACE_WITH_API_TOKEN",
"Content-Type: application/json",
"Accept: application/json",
],
]);
$response = curl_exec($curl);
if (curl_errno($curl)) {
echo 'Error:' . curl_error($curl);
}
curl_close($curl);
echo $response;
$response = Http::withToken('REPLACE_WITH_API_TOKEN')
->acceptJson()
->post('https://api.provero.io/api/validate/uk-address', [
'query' => '10 Downing Street, London, SW1A 2AA',
'postcode' => 'SW1A 2AA',
'post_town' => 'London',
]);
return $response->json();
// Run on your server with Node.js 18+. Keep your API token out of browser code.
const response = await fetch("https://api.provero.io/api/validate/uk-address", {
method: "POST",
headers: {
"Authorization": `Bearer ${process.env.PROVERO_API_TOKEN}`,
"Content-Type": "application/json",
"Accept": "application/json"
},
body: JSON.stringify({
query: "10 Downing Street, London, SW1A 2AA",
postcode: "SW1A 2AA",
post_town: "London"
})
});
console.log(response.status);
console.log(await response.json());
curl -X POST https://api.provero.io/api/validate/uk-address \
-H "Authorization: Bearer REPLACE_WITH_API_TOKEN" \
-H "Content-Type: application/json" \
-H "Accept: application/json" \
-d '{
"query": "10 Downing Street, London, SW1A 2AA",
"postcode": "SW1A 2AA",
"post_town": "London"
}'
Response Examples
Success - Match
{
"query": "10 Downing Street, London, SW1A 2AA",
"valid": true,
"address_complete": true,
"confidence": 1,
"count": 1,
"fit": 1,
"organisation_match": "FULL",
"premise_match": "FULL",
"postcode_match": "FULL",
"thoroughfare_match": "FULL",
"locality_match": "FULL",
"post_town_match": "FULL",
"match": {
"organisation_name": "Prime Minister & First Lord Of The Treasury",
"department_name": "",
"po_box": "",
"building_name": "",
"sub_building_name": "",
"building_number": "10",
"premise": "10",
"dependant_thoroughfare": "",
"thoroughfare": "Downing Street",
"double_dependant_locality": "",
"dependant_locality": "",
"post_town": "London",
"postcode": "SW1A 2AA",
"line_1": "Prime Minister & First Lord Of The Treasury",
"line_2": "10 Downing Street",
"line_3": "",
"formatted_address": "Prime Minister & First Lord Of The Treasury, 10 Downing Street, London, SW1A 2AA",
"country": "England",
"country_iso_2": "GB",
"latitude": 51.503541,
"longitude": -0.12767
}
}
Success - No Match
{
"query": "Unknown address, ZZ1 1ZZ",
"valid": false,
"address_complete": false,
"confidence": 0,
"count": 0,
"fit": 0,
"organisation_match": "NO_MATCH",
"premise_match": "NO_MATCH",
"postcode_match": "NO_MATCH",
"thoroughfare_match": "NO_MATCH",
"locality_match": "NO_MATCH",
"post_town_match": "NO_MATCH",
"match": null,
"requestError": {
"serviceException": {
"messageId": "No matching PAF address found.",
"code": 404
}
}
}
Validation Error - Query Missing
{
"message": "The query field is required.",
"errors": {
"query": [
"The query field is required."
]
}
}
Validation Error - Postcode Too Long
{
"message": "The postcode field must not be greater than 16 characters.",
"errors": {
"postcode": [
"The postcode field must not be greater than 16 characters."
]
}
}
Payment Required - Insufficient Balance
{
"message": "Insufficient balance for validation request.",
"service": "uk-address",
"required_amount": "0.0460000000",
"current_balance": "0.0000000000"
}
Validation Error - Input Rejected (400)
{
"requestError": {
"serviceException": {
"messageId": "The address could not be checked. Check the address and try again.",
"code": 400,
"errorCode": "UK_ADDRESS_INPUT_REJECTED"
}
}
}
Additional response examples 2
Application Error - Temporarily Unavailable (503)
{
"requestError": {
"serviceException": {
"messageId": "UK address validation is temporarily unavailable. Please try again later.",
"code": 503,
"errorCode": "UK_ADDRESS_UNAVAILABLE"
}
}
}
Application Error - Service Unavailable (502)
{
"requestError": {
"serviceException": {
"messageId": "UK address validation is temporarily unavailable. Please try again later.",
"code": 502,
"errorCode": "UK_ADDRESS_UNAVAILABLE"
}
}
}
Response Body
Success structure
| Field Name | Type | Example | Always Present | Description |
|---|---|---|---|---|
count |
integer |
1 | Yes | Number of candidates, from 0 to 10. Only the best candidate is returned in match. |
fit |
number |
1 | Yes | Closeness of the input to the candidate, between 0 and 1. Zero for no match. |
organisation_match |
string |
FULL | Yes | Component match status: FULL, PARTIAL, INCORRECT, MISSING or NA. NO_MATCH when no candidate exists. |
premise_match |
string |
FULL | Yes | Component match status: FULL, PARTIAL, INCORRECT, MISSING or NA. NO_MATCH when no candidate exists. |
postcode_match |
string |
FULL | Yes | Postcode match status after safe case and whitespace normalisation: FULL, PARTIAL, INCORRECT, MISSING or NA. NO_MATCH when no candidate exists. |
thoroughfare_match |
string |
FULL | Yes | Component match status: FULL, PARTIAL, INCORRECT, MISSING or NA. NO_MATCH when no candidate exists. |
locality_match |
string |
FULL | Yes | Component match status: FULL, PARTIAL, INCORRECT, MISSING or NA. NO_MATCH when no candidate exists. |
post_town_match |
string |
FULL | Yes | Component match status: FULL, PARTIAL, INCORRECT, MISSING or NA. NO_MATCH when no candidate exists. |
query |
string |
10 Downing Street, London, SW1A 2AA | Yes | The submitted free-form address query. |
valid |
boolean |
true | Yes | True when a PAF candidate was found. This does not mean the input was an exact match. |
address_complete |
boolean |
true | Yes | True only for one candidate with all six component statuses FULL or NA and no fuzzy, unusable or conflicting supplied postcode. Otherwise review the suggested address. |
confidence |
number |
0.863 | Yes | Matching confidence between 0 and 1. Zero for no match. |
match |
object|null |
{"building_number":"10","line_2":"10 Downing Street","post_town":"London","postcode":"SW1A 2AA"} | Yes | Canonical PAF address match. Null is only returned on a 404 no-match response. |
match.organisation_name |
string |
Prime Minister & First Lord Of The Treasury | No | Canonical organisation name. |
match.department_name |
string |
No | Canonical department name. | |
match.po_box |
string |
No | Canonical PO box. | |
match.building_name |
string |
No | Canonical building name. | |
match.building_number |
string |
10 | No | Canonical building number. |
match.dependant_thoroughfare |
string |
No | Canonical dependent thoroughfare. | |
match.thoroughfare |
string |
Downing Street | No | Canonical thoroughfare. |
match.double_dependant_locality |
string |
No | Canonical double dependent locality. | |
match.dependant_locality |
string |
No | Canonical dependent locality. | |
match.post_town |
string |
London | No | Canonical post town. |
match.postcode |
string |
SW1A 2AA | No | Canonical postcode. |
Error structure
| Field Name | Type | Example | Always Present | Description |
|---|---|---|---|---|
message |
string |
The query field is required. | No | Top-level error message returned for malformed requests, insufficient balance, or service errors. |
errors |
object |
{"query": ["The query field is required."]} | No | These requests are rejected before lookup and are not charged. |
requestError |
object |
{"serviceException": {"messageId": "No matching PAF address found.", "code": 404}} | No | Returned when no PAF match is found or the address validation service cannot process the request. |
service |
string |
uk-address | No | Service alias returned with a 402 insufficient-balance response. |
required_amount |
string |
0.0460000000 | No | Credit amount required to process the validation request. |
current_balance |
string |
0.0000000000 | No | Current available balance at the time the request was rejected. |