Store New Customer
Create the Azotte-side projection of a customer using identity data sourced from your system. Returns the canonical AzotteCustomer record (including CustomerUrn).
URL
POST /api/c2a/customer/store
Request Parameters
Body: StoreCustomerRequest.
| Name | Type | Description |
|---|---|---|
customer | object (CustomerDto) | Required. Customer payload. |
claimedRegion | object (ClaimedRegion) | Required. Country / language context claimed by the caller. Scopes storefront, currency, tax. |
CustomerDto
| Name | Type | Description |
|---|---|---|
externalIdentifier | string | Required. Tenant-side identifier. Must be unique per tenant. |
email | string | Customer email. |
phoneNumber | string | E.164 phone number. |
salutation | string | Salutation prefix. |
firstName | string | Given name. |
lastName | string | Family name. |
gender | string (EnGender) | Gender code. |
legalType | string (EnPersonLegalType) | Individual or Corporate. |
primaryBillingAddress | object (PostalAddress) | Billing address. |
corporationInfo | object (CorporationInfo) | Conditional. Required when legalType = Corporate. |
privacy | object (AzotteCustomerPrivacySettings) | Communication consents. |
status | string | Caller-asserted status. |
ClaimedRegion
| Name | Type | Description |
|---|---|---|
countryCode | string | Required. ISO 3166-1 alpha-2 country code. |
languageCode | string | Required. ISO 639-1 language code. |
Request Example
{
"customer": {
"externalIdentifier": "crm-9981273",
"email": "jane.doe@example.com",
"phoneNumber": "+49 170 1234567",
"salutation": "Ms.",
"firstName": "Jane",
"lastName": "Doe",
"gender": "Female",
"legalType": "Individual",
"primaryBillingAddress": {
"street": "Hauptstr. 1",
"city": "Berlin",
"postalCode": "10115",
"countryCode": "DE"
}
},
"claimedRegion": {
"countryCode": "DE",
"languageCode": "de"
}
}
Response Parameters
StoreCustomerResponse.
| Name | Type | Description |
|---|---|---|
result | object (AzotteCustomer) | Canonical customer record. |
result.customerUrn | string | Azotte-assigned URN. Use this in every downstream call. |
result.externalIdentifier | string | Echo of supplied ExternalId. |
result.email | string | Echoed email. |
result.status | string | Operational status (Active, etc.). |
status | object (AzotteStatus) | Operation status envelope. |
status.messageCode | string | SUCCESS on hit. |
Sample Response
{
"result": {
"customerUrn": "cu.00.482",
"externalIdentifier": "crm-9981273",
"email": "jane.doe@example.com",
"status": "Active"
},
"status": { "messageCode": "SUCCESS" }
}
Bad Request (HTTP 400)
messageCode | Trigger |
|---|---|
BAD_REQUEST | request.Customer is null. |
INVALID_REQUEST | FluentValidation rule failed on payload. |
Conflict (HTTP 409)
Duplicate identity collision.
messageCode | Trigger |
|---|---|
USER_WITH_SAME_PHONE_NUMBER_EXISTS | Phone number already attached to another customer. |
USER_WITH_SAME_EMAIL_EXISTS | Email already attached to another customer. |
CUSTOMER_ALREADY_STORED | externalIdentifier already projected (call /info or /update instead). |
Server Error (HTTP 500)
messageCode | Trigger |
|---|---|
SQL_DATABASE_FAILURE | Insert returned null (DB layer rejected the row). |
INTERNAL_SERVER_ERROR | Unhandled exception caught by the controller. |
Behaviour
- ExternalId uniqueness is enforced per tenant. Colliding ExternalId returns
CUSTOMER_ALREADY_STORED(409). - Email and phone uniqueness enforced per tenant — return
USER_WITH_SAME_EMAIL_EXISTS/USER_WITH_SAME_PHONE_NUMBER_EXISTS(409). - Validation of mandatory tenant-side fields runs via
TenantCustomerInfoStorageValidator→INVALID_REQUEST(400). - Privacy / consent flags are stored verbatim; you remain responsible for the legal basis.
Sample Codes
- cURL
- JavaScript
- Node.js
- Python
- Java
- C#
- PHP
- Go
curl --location 'https://acme.sandbox.azotte.com/api/v1/c2a/customer/store' \
--header 'Content-Type: application/json' \
--header 'x-tn: e2a1c7b2-4f3a-4b8e-9c2d-1a2b3c4d5e6f' \
--header 'x-api-key: sk_dev_acme_sample_123456789' \
--data '{
"customer": {
"externalIdentifier": "crm-9981273",
"email": "jane.doe@example.com",
"firstName": "Jane",
"lastName": "Doe",
"legalType": "Individual"
},
"claimedRegion": { "countryCode": "DE", "languageCode": "de" }
}'
const payload = {
customer: {
externalIdentifier: 'crm-9981273',
email: 'jane.doe@example.com',
firstName: 'Jane',
lastName: 'Doe',
legalType: 'Individual'
},
claimedRegion: { countryCode: 'DE', languageCode: 'de' }
};
const res = await fetch('https://acme.sandbox.azotte.com/api/v1/c2a/customer/store', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'x-tn': 'e2a1c7b2-4f3a-4b8e-9c2d-1a2b3c4d5e6f',
'x-api-key': 'sk_dev_acme_sample_123456789'
},
body: JSON.stringify(payload)
});
console.log(await res.json());
import { request } from 'undici';
const payload = {
customer: {
externalIdentifier: 'crm-9981273',
email: 'jane.doe@example.com',
firstName: 'Jane',
lastName: 'Doe',
legalType: 'Individual'
},
claimedRegion: { countryCode: 'DE', languageCode: 'de' }
};
const { body } = await request('https://acme.sandbox.azotte.com/api/v1/c2a/customer/store', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'x-tn': 'e2a1c7b2-4f3a-4b8e-9c2d-1a2b3c4d5e6f',
'x-api-key': 'sk_dev_acme_sample_123456789'
},
body: JSON.stringify(payload)
});
console.log(await body.json());
import requests
payload = {
"customer": {
"externalIdentifier": "crm-9981273",
"email": "jane.doe@example.com",
"firstName": "Jane",
"lastName": "Doe",
"legalType": "Individual",
},
"claimedRegion": {"countryCode": "DE", "languageCode": "de"},
}
res = requests.post(
"https://acme.sandbox.azotte.com/api/v1/c2a/customer/store",
headers={
"Content-Type": "application/json",
"x-tn": "e2a1c7b2-4f3a-4b8e-9c2d-1a2b3c4d5e6f",
"x-api-key": "sk_dev_acme_sample_123456789",
},
json=payload,
)
print(res.json())
import java.net.URI;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;
String json = """
{
"customer": {
"externalIdentifier": "crm-9981273",
"email": "jane.doe@example.com",
"firstName": "Jane",
"lastName": "Doe",
"legalType": "Individual"
},
"claimedRegion": { "countryCode": "DE", "languageCode": "de" }
}
""";
HttpClient client = HttpClient.newHttpClient();
HttpRequest req = HttpRequest.newBuilder()
.uri(URI.create("https://acme.sandbox.azotte.com/api/v1/c2a/customer/store"))
.header("Content-Type", "application/json")
.header("x-tn", "e2a1c7b2-4f3a-4b8e-9c2d-1a2b3c4d5e6f")
.header("x-api-key", "sk_dev_acme_sample_123456789")
.POST(HttpRequest.BodyPublishers.ofString(json))
.build();
HttpResponse<String> res = client.send(req, HttpResponse.BodyHandlers.ofString());
System.out.println(res.body());
using System.Net.Http.Json;
var payload = new {
customer = new {
externalIdentifier = "crm-9981273",
email = "jane.doe@example.com",
firstName = "Jane",
lastName = "Doe",
legalType = "Individual"
},
claimedRegion = new { countryCode = "DE", languageCode = "de" }
};
using var http = new HttpClient();
http.DefaultRequestHeaders.Add("x-tn", "e2a1c7b2-4f3a-4b8e-9c2d-1a2b3c4d5e6f");
http.DefaultRequestHeaders.Add("x-api-key", "sk_dev_acme_sample_123456789");
var res = await http.PostAsJsonAsync(
"https://acme.sandbox.azotte.com/api/v1/c2a/customer/store",
payload);
Console.WriteLine(await res.Content.ReadAsStringAsync());
<?php
$payload = [
'customer' => [
'externalIdentifier' => 'crm-9981273',
'email' => 'jane.doe@example.com',
'firstName' => 'Jane',
'lastName' => 'Doe',
'legalType' => 'Individual',
],
'claimedRegion' => ['countryCode' => 'DE', 'languageCode' => 'de'],
];
$ch = curl_init('https://acme.sandbox.azotte.com/api/v1/c2a/customer/store');
curl_setopt_array($ch, [
CURLOPT_RETURNTRANSFER => true,
CURLOPT_POST => true,
CURLOPT_HTTPHEADER => [
'Content-Type: application/json',
'x-tn: e2a1c7b2-4f3a-4b8e-9c2d-1a2b3c4d5e6f',
'x-api-key: sk_dev_acme_sample_123456789',
],
CURLOPT_POSTFIELDS => json_encode($payload),
]);
echo curl_exec($ch);
curl_close($ch);
package main
import (
"bytes"
"encoding/json"
"fmt"
"io"
"net/http"
)
func main() {
payload := map[string]any{
"customer": map[string]any{
"externalIdentifier": "crm-9981273",
"email": "jane.doe@example.com",
"firstName": "Jane",
"lastName": "Doe",
"legalType": "Individual",
},
"claimedRegion": map[string]string{"countryCode": "DE", "languageCode": "de"},
}
body, _ := json.Marshal(payload)
req, _ := http.NewRequest("POST",
"https://acme.sandbox.azotte.com/api/v1/c2a/customer/store",
bytes.NewReader(body))
req.Header.Set("Content-Type", "application/json")
req.Header.Set("x-tn", "e2a1c7b2-4f3a-4b8e-9c2d-1a2b3c4d5e6f")
req.Header.Set("x-api-key", "sk_dev_acme_sample_123456789")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
out, _ := io.ReadAll(res.Body)
fmt.Println(string(out))
}