Onboard
Initialise a site and its assets, and enrol them in a proposition in a single call.
This endpoint will:
- Upsert the site and asset(s)
- Enrol in the relevant flex proposition
The response returns the site and asset IDs you’ll use in subsequent calls, and the enrolment outcome.
Onboarding is idempotent and atomic — sending the same site or asset returns the existing record with any new fields merged in; if enrolment fails, nothing is stored.
curl --request POST \
--url https://api-sandbox.axle.energy/entities/site/onboard \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--data '
{
"site": {
"mpan": "1234567890123",
"postcode": "SW1A 1AA",
"street_address": "10 Downing Street",
"email": "resident@example.com",
"gave_boundary_meter_consent_at": "2026-01-15T10:30:00Z"
},
"assets": [
{
"external_id": "<string>",
"type": "charger",
"properties": {
"power_kw": 7.4
},
"asset_model": "<string>",
"installation_date": "2023-12-25"
}
],
"override_withdrawal": false
}
'import requests
url = "https://api-sandbox.axle.energy/entities/site/onboard"
payload = {
"site": {
"mpan": "1234567890123",
"postcode": "SW1A 1AA",
"street_address": "10 Downing Street",
"email": "resident@example.com",
"gave_boundary_meter_consent_at": "2026-01-15T10:30:00Z"
},
"assets": [
{
"external_id": "<string>",
"type": "charger",
"properties": { "power_kw": 7.4 },
"asset_model": "<string>",
"installation_date": "2023-12-25"
}
],
"override_withdrawal": False
}
headers = {
"Authorization": "Bearer <token>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {Authorization: 'Bearer <token>', 'Content-Type': 'application/json'},
body: JSON.stringify({
site: {
mpan: '1234567890123',
postcode: 'SW1A 1AA',
street_address: '10 Downing Street',
email: 'resident@example.com',
gave_boundary_meter_consent_at: '2026-01-15T10:30:00Z'
},
assets: [
{
external_id: '<string>',
type: 'charger',
properties: {power_kw: 7.4},
asset_model: '<string>',
installation_date: '2023-12-25'
}
],
override_withdrawal: false
})
};
fetch('https://api-sandbox.axle.energy/entities/site/onboard', 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-sandbox.axle.energy/entities/site/onboard",
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([
'site' => [
'mpan' => '1234567890123',
'postcode' => 'SW1A 1AA',
'street_address' => '10 Downing Street',
'email' => 'resident@example.com',
'gave_boundary_meter_consent_at' => '2026-01-15T10:30:00Z'
],
'assets' => [
[
'external_id' => '<string>',
'type' => 'charger',
'properties' => [
'power_kw' => 7.4
],
'asset_model' => '<string>',
'installation_date' => '2023-12-25'
]
],
'override_withdrawal' => false
]),
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>",
"Content-Type: application/json"
],
]);
$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-sandbox.axle.energy/entities/site/onboard"
payload := strings.NewReader("{\n \"site\": {\n \"mpan\": \"1234567890123\",\n \"postcode\": \"SW1A 1AA\",\n \"street_address\": \"10 Downing Street\",\n \"email\": \"resident@example.com\",\n \"gave_boundary_meter_consent_at\": \"2026-01-15T10:30:00Z\"\n },\n \"assets\": [\n {\n \"external_id\": \"<string>\",\n \"type\": \"charger\",\n \"properties\": {\n \"power_kw\": 7.4\n },\n \"asset_model\": \"<string>\",\n \"installation_date\": \"2023-12-25\"\n }\n ],\n \"override_withdrawal\": false\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("Authorization", "Bearer <token>")
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-sandbox.axle.energy/entities/site/onboard")
.header("Authorization", "Bearer <token>")
.header("Content-Type", "application/json")
.body("{\n \"site\": {\n \"mpan\": \"1234567890123\",\n \"postcode\": \"SW1A 1AA\",\n \"street_address\": \"10 Downing Street\",\n \"email\": \"resident@example.com\",\n \"gave_boundary_meter_consent_at\": \"2026-01-15T10:30:00Z\"\n },\n \"assets\": [\n {\n \"external_id\": \"<string>\",\n \"type\": \"charger\",\n \"properties\": {\n \"power_kw\": 7.4\n },\n \"asset_model\": \"<string>\",\n \"installation_date\": \"2023-12-25\"\n }\n ],\n \"override_withdrawal\": false\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://api-sandbox.axle.energy/entities/site/onboard")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["Authorization"] = 'Bearer <token>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"site\": {\n \"mpan\": \"1234567890123\",\n \"postcode\": \"SW1A 1AA\",\n \"street_address\": \"10 Downing Street\",\n \"email\": \"resident@example.com\",\n \"gave_boundary_meter_consent_at\": \"2026-01-15T10:30:00Z\"\n },\n \"assets\": [\n {\n \"external_id\": \"<string>\",\n \"type\": \"charger\",\n \"properties\": {\n \"power_kw\": 7.4\n },\n \"asset_model\": \"<string>\",\n \"installation_date\": \"2023-12-25\"\n }\n ],\n \"override_withdrawal\": false\n}"
response = http.request(request)
puts response.read_body{
"site": {
"site_id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"site_created": true,
"fields_updated": [],
"warnings": []
},
"assets": [
{
"asset_id": "b2c3d4e5-f6a7-8901-bcde-f23456789012",
"external_id": "charger-001",
"asset_created": true,
"fields_updated": [],
"warnings": []
}
],
"enrolment": {
"site_id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"status": "enrolled"
}
}/onboard-site-and-asset?
It’s still supported, but we’d recommend migrating to /onboard when convenient.Authorizations
The access token received from the authorization server in the OAuth 2.0 flow.
Body
Request model for the onboard endpoint.
Site information
Show child attributes
Show child attributes
{
"mpan": "1234567890123",
"postcode": "SW1A 1AA",
"street_address": "10 Downing Street",
"email": "resident@example.com",
"gave_boundary_meter_consent_at": "2026-01-15T10:30:00Z"
}
One or more assets to register at the site
Show child attributes
Show child attributes
[
{
"external_id": "charger-001",
"type": "charger",
"asset_model": "zappi",
"installation_date": "2025-06-15",
"properties": { "power_kw": 7.4 }
}
]
Proposition to enrol the site in
limited_pause, full_asset_schedule_control Set to true to re-enrol regardless of previous withdrawals.
false
Response
Site and assets persisted, site enrolled in proposition
Was this page helpful?
curl --request POST \
--url https://api-sandbox.axle.energy/entities/site/onboard \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--data '
{
"site": {
"mpan": "1234567890123",
"postcode": "SW1A 1AA",
"street_address": "10 Downing Street",
"email": "resident@example.com",
"gave_boundary_meter_consent_at": "2026-01-15T10:30:00Z"
},
"assets": [
{
"external_id": "<string>",
"type": "charger",
"properties": {
"power_kw": 7.4
},
"asset_model": "<string>",
"installation_date": "2023-12-25"
}
],
"override_withdrawal": false
}
'import requests
url = "https://api-sandbox.axle.energy/entities/site/onboard"
payload = {
"site": {
"mpan": "1234567890123",
"postcode": "SW1A 1AA",
"street_address": "10 Downing Street",
"email": "resident@example.com",
"gave_boundary_meter_consent_at": "2026-01-15T10:30:00Z"
},
"assets": [
{
"external_id": "<string>",
"type": "charger",
"properties": { "power_kw": 7.4 },
"asset_model": "<string>",
"installation_date": "2023-12-25"
}
],
"override_withdrawal": False
}
headers = {
"Authorization": "Bearer <token>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {Authorization: 'Bearer <token>', 'Content-Type': 'application/json'},
body: JSON.stringify({
site: {
mpan: '1234567890123',
postcode: 'SW1A 1AA',
street_address: '10 Downing Street',
email: 'resident@example.com',
gave_boundary_meter_consent_at: '2026-01-15T10:30:00Z'
},
assets: [
{
external_id: '<string>',
type: 'charger',
properties: {power_kw: 7.4},
asset_model: '<string>',
installation_date: '2023-12-25'
}
],
override_withdrawal: false
})
};
fetch('https://api-sandbox.axle.energy/entities/site/onboard', 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-sandbox.axle.energy/entities/site/onboard",
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([
'site' => [
'mpan' => '1234567890123',
'postcode' => 'SW1A 1AA',
'street_address' => '10 Downing Street',
'email' => 'resident@example.com',
'gave_boundary_meter_consent_at' => '2026-01-15T10:30:00Z'
],
'assets' => [
[
'external_id' => '<string>',
'type' => 'charger',
'properties' => [
'power_kw' => 7.4
],
'asset_model' => '<string>',
'installation_date' => '2023-12-25'
]
],
'override_withdrawal' => false
]),
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>",
"Content-Type: application/json"
],
]);
$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-sandbox.axle.energy/entities/site/onboard"
payload := strings.NewReader("{\n \"site\": {\n \"mpan\": \"1234567890123\",\n \"postcode\": \"SW1A 1AA\",\n \"street_address\": \"10 Downing Street\",\n \"email\": \"resident@example.com\",\n \"gave_boundary_meter_consent_at\": \"2026-01-15T10:30:00Z\"\n },\n \"assets\": [\n {\n \"external_id\": \"<string>\",\n \"type\": \"charger\",\n \"properties\": {\n \"power_kw\": 7.4\n },\n \"asset_model\": \"<string>\",\n \"installation_date\": \"2023-12-25\"\n }\n ],\n \"override_withdrawal\": false\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("Authorization", "Bearer <token>")
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-sandbox.axle.energy/entities/site/onboard")
.header("Authorization", "Bearer <token>")
.header("Content-Type", "application/json")
.body("{\n \"site\": {\n \"mpan\": \"1234567890123\",\n \"postcode\": \"SW1A 1AA\",\n \"street_address\": \"10 Downing Street\",\n \"email\": \"resident@example.com\",\n \"gave_boundary_meter_consent_at\": \"2026-01-15T10:30:00Z\"\n },\n \"assets\": [\n {\n \"external_id\": \"<string>\",\n \"type\": \"charger\",\n \"properties\": {\n \"power_kw\": 7.4\n },\n \"asset_model\": \"<string>\",\n \"installation_date\": \"2023-12-25\"\n }\n ],\n \"override_withdrawal\": false\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://api-sandbox.axle.energy/entities/site/onboard")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["Authorization"] = 'Bearer <token>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"site\": {\n \"mpan\": \"1234567890123\",\n \"postcode\": \"SW1A 1AA\",\n \"street_address\": \"10 Downing Street\",\n \"email\": \"resident@example.com\",\n \"gave_boundary_meter_consent_at\": \"2026-01-15T10:30:00Z\"\n },\n \"assets\": [\n {\n \"external_id\": \"<string>\",\n \"type\": \"charger\",\n \"properties\": {\n \"power_kw\": 7.4\n },\n \"asset_model\": \"<string>\",\n \"installation_date\": \"2023-12-25\"\n }\n ],\n \"override_withdrawal\": false\n}"
response = http.request(request)
puts response.read_body{
"site": {
"site_id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"site_created": true,
"fields_updated": [],
"warnings": []
},
"assets": [
{
"asset_id": "b2c3d4e5-f6a7-8901-bcde-f23456789012",
"external_id": "charger-001",
"asset_created": true,
"fields_updated": [],
"warnings": []
}
],
"enrolment": {
"site_id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"status": "enrolled"
}
}
