curl --request POST \
--url https://api.jtl-cloud.com/erp/v2/purchase-orders/{purchaseOrderId}/line-items \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--header 'x-tenant-id: <x-tenant-id>' \
--data '
{
"itemId": "b45f6432-2462-4c6f-b00f-1d9d01000000",
"quantity": 123,
"netPurchasePriceAmount": 123,
"vatRatePercentage": 123,
"supplierItemNumber": "<string>",
"deliveryDate": "2023-11-07T05:31:56Z",
"note": "<string>"
}
'import requests
url = "https://api.jtl-cloud.com/erp/v2/purchase-orders/{purchaseOrderId}/line-items"
payload = {
"itemId": "b45f6432-2462-4c6f-b00f-1d9d01000000",
"quantity": 123,
"netPurchasePriceAmount": 123,
"vatRatePercentage": 123,
"supplierItemNumber": "<string>",
"deliveryDate": "2023-11-07T05:31:56Z",
"note": "<string>"
}
headers = {
"x-tenant-id": "<x-tenant-id>",
"Authorization": "Bearer <token>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {
'x-tenant-id': '<x-tenant-id>',
Authorization: 'Bearer <token>',
'Content-Type': 'application/json'
},
body: JSON.stringify({
itemId: 'b45f6432-2462-4c6f-b00f-1d9d01000000',
quantity: 123,
netPurchasePriceAmount: 123,
vatRatePercentage: 123,
supplierItemNumber: '<string>',
deliveryDate: '2023-11-07T05:31:56Z',
note: '<string>'
})
};
fetch('https://api.jtl-cloud.com/erp/v2/purchase-orders/{purchaseOrderId}/line-items', 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.jtl-cloud.com/erp/v2/purchase-orders/{purchaseOrderId}/line-items",
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([
'itemId' => 'b45f6432-2462-4c6f-b00f-1d9d01000000',
'quantity' => 123,
'netPurchasePriceAmount' => 123,
'vatRatePercentage' => 123,
'supplierItemNumber' => '<string>',
'deliveryDate' => '2023-11-07T05:31:56Z',
'note' => '<string>'
]),
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>",
"Content-Type: application/json",
"x-tenant-id: <x-tenant-id>"
],
]);
$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.jtl-cloud.com/erp/v2/purchase-orders/{purchaseOrderId}/line-items"
payload := strings.NewReader("{\n \"itemId\": \"b45f6432-2462-4c6f-b00f-1d9d01000000\",\n \"quantity\": 123,\n \"netPurchasePriceAmount\": 123,\n \"vatRatePercentage\": 123,\n \"supplierItemNumber\": \"<string>\",\n \"deliveryDate\": \"2023-11-07T05:31:56Z\",\n \"note\": \"<string>\"\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("x-tenant-id", "<x-tenant-id>")
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.jtl-cloud.com/erp/v2/purchase-orders/{purchaseOrderId}/line-items")
.header("x-tenant-id", "<x-tenant-id>")
.header("Authorization", "Bearer <token>")
.header("Content-Type", "application/json")
.body("{\n \"itemId\": \"b45f6432-2462-4c6f-b00f-1d9d01000000\",\n \"quantity\": 123,\n \"netPurchasePriceAmount\": 123,\n \"vatRatePercentage\": 123,\n \"supplierItemNumber\": \"<string>\",\n \"deliveryDate\": \"2023-11-07T05:31:56Z\",\n \"note\": \"<string>\"\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://api.jtl-cloud.com/erp/v2/purchase-orders/{purchaseOrderId}/line-items")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["x-tenant-id"] = '<x-tenant-id>'
request["Authorization"] = 'Bearer <token>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"itemId\": \"b45f6432-2462-4c6f-b00f-1d9d01000000\",\n \"quantity\": 123,\n \"netPurchasePriceAmount\": 123,\n \"vatRatePercentage\": 123,\n \"supplierItemNumber\": \"<string>\",\n \"deliveryDate\": \"2023-11-07T05:31:56Z\",\n \"note\": \"<string>\"\n}"
response = http.request(request)
puts response.read_body{
"lineItemId": "b45f6432-2462-4c6f-b00f-1d9d01000000"
}{
"type": "https://www.rfc-editor.org/rfc/rfc7231#section-6.5.1",
"title": "One or more validation errors occurred.",
"status": 400,
"instance": "/api/route",
"traceId": "0HMPNHL0JHL76:00000001",
"detail": "<string>",
"errors": [
{
"name": "Error or field name",
"reason": "Error reason",
"code": "<string>",
"severity": "<string>"
}
]
}{
"type": "https://www.rfc-editor.org/rfc/rfc7231#section-6.5.1",
"title": "One or more validation errors occurred.",
"status": 400,
"instance": "/api/route",
"traceId": "0HMPNHL0JHL76:00000001",
"detail": "<string>",
"errors": [
{
"name": "Error or field name",
"reason": "Error reason",
"code": "<string>",
"severity": "<string>"
}
]
}{
"type": "https://www.rfc-editor.org/rfc/rfc7231#section-6.5.1",
"title": "One or more validation errors occurred.",
"status": 400,
"instance": "/api/route",
"traceId": "0HMPNHL0JHL76:00000001",
"detail": "<string>",
"errors": [
{
"name": "Error or field name",
"reason": "Error reason",
"code": "<string>",
"severity": "<string>"
}
]
}{
"type": "https://www.rfc-editor.org/rfc/rfc7231#section-6.5.1",
"title": "One or more validation errors occurred.",
"status": 400,
"instance": "/api/route",
"traceId": "0HMPNHL0JHL76:00000001",
"detail": "<string>",
"errors": [
{
"name": "Error or field name",
"reason": "Error reason",
"code": "<string>",
"severity": "<string>"
}
]
}{
"type": "https://www.rfc-editor.org/rfc/rfc7231#section-6.5.1",
"title": "One or more validation errors occurred.",
"status": 400,
"instance": "/api/route",
"traceId": "0HMPNHL0JHL76:00000001",
"detail": "<string>",
"errors": [
{
"name": "Error or field name",
"reason": "Error reason",
"code": "<string>",
"severity": "<string>"
}
]
}Create Purchase Order Line Item
Adds one article position to an existing purchase order. The order must be Open or Released — from InProgress onwards the position would already be part of a goods receipt. The article must already be assigned to the order’s supplier; this endpoint never creates that assignment. Fields the caller omits are resolved from the supplier’s master data, so the smallest useful request carries the article, the quantity, the net price and the VAT rate.
curl --request POST \
--url https://api.jtl-cloud.com/erp/v2/purchase-orders/{purchaseOrderId}/line-items \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--header 'x-tenant-id: <x-tenant-id>' \
--data '
{
"itemId": "b45f6432-2462-4c6f-b00f-1d9d01000000",
"quantity": 123,
"netPurchasePriceAmount": 123,
"vatRatePercentage": 123,
"supplierItemNumber": "<string>",
"deliveryDate": "2023-11-07T05:31:56Z",
"note": "<string>"
}
'import requests
url = "https://api.jtl-cloud.com/erp/v2/purchase-orders/{purchaseOrderId}/line-items"
payload = {
"itemId": "b45f6432-2462-4c6f-b00f-1d9d01000000",
"quantity": 123,
"netPurchasePriceAmount": 123,
"vatRatePercentage": 123,
"supplierItemNumber": "<string>",
"deliveryDate": "2023-11-07T05:31:56Z",
"note": "<string>"
}
headers = {
"x-tenant-id": "<x-tenant-id>",
"Authorization": "Bearer <token>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {
'x-tenant-id': '<x-tenant-id>',
Authorization: 'Bearer <token>',
'Content-Type': 'application/json'
},
body: JSON.stringify({
itemId: 'b45f6432-2462-4c6f-b00f-1d9d01000000',
quantity: 123,
netPurchasePriceAmount: 123,
vatRatePercentage: 123,
supplierItemNumber: '<string>',
deliveryDate: '2023-11-07T05:31:56Z',
note: '<string>'
})
};
fetch('https://api.jtl-cloud.com/erp/v2/purchase-orders/{purchaseOrderId}/line-items', 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.jtl-cloud.com/erp/v2/purchase-orders/{purchaseOrderId}/line-items",
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([
'itemId' => 'b45f6432-2462-4c6f-b00f-1d9d01000000',
'quantity' => 123,
'netPurchasePriceAmount' => 123,
'vatRatePercentage' => 123,
'supplierItemNumber' => '<string>',
'deliveryDate' => '2023-11-07T05:31:56Z',
'note' => '<string>'
]),
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>",
"Content-Type: application/json",
"x-tenant-id: <x-tenant-id>"
],
]);
$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.jtl-cloud.com/erp/v2/purchase-orders/{purchaseOrderId}/line-items"
payload := strings.NewReader("{\n \"itemId\": \"b45f6432-2462-4c6f-b00f-1d9d01000000\",\n \"quantity\": 123,\n \"netPurchasePriceAmount\": 123,\n \"vatRatePercentage\": 123,\n \"supplierItemNumber\": \"<string>\",\n \"deliveryDate\": \"2023-11-07T05:31:56Z\",\n \"note\": \"<string>\"\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("x-tenant-id", "<x-tenant-id>")
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.jtl-cloud.com/erp/v2/purchase-orders/{purchaseOrderId}/line-items")
.header("x-tenant-id", "<x-tenant-id>")
.header("Authorization", "Bearer <token>")
.header("Content-Type", "application/json")
.body("{\n \"itemId\": \"b45f6432-2462-4c6f-b00f-1d9d01000000\",\n \"quantity\": 123,\n \"netPurchasePriceAmount\": 123,\n \"vatRatePercentage\": 123,\n \"supplierItemNumber\": \"<string>\",\n \"deliveryDate\": \"2023-11-07T05:31:56Z\",\n \"note\": \"<string>\"\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://api.jtl-cloud.com/erp/v2/purchase-orders/{purchaseOrderId}/line-items")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["x-tenant-id"] = '<x-tenant-id>'
request["Authorization"] = 'Bearer <token>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"itemId\": \"b45f6432-2462-4c6f-b00f-1d9d01000000\",\n \"quantity\": 123,\n \"netPurchasePriceAmount\": 123,\n \"vatRatePercentage\": 123,\n \"supplierItemNumber\": \"<string>\",\n \"deliveryDate\": \"2023-11-07T05:31:56Z\",\n \"note\": \"<string>\"\n}"
response = http.request(request)
puts response.read_body{
"lineItemId": "b45f6432-2462-4c6f-b00f-1d9d01000000"
}{
"type": "https://www.rfc-editor.org/rfc/rfc7231#section-6.5.1",
"title": "One or more validation errors occurred.",
"status": 400,
"instance": "/api/route",
"traceId": "0HMPNHL0JHL76:00000001",
"detail": "<string>",
"errors": [
{
"name": "Error or field name",
"reason": "Error reason",
"code": "<string>",
"severity": "<string>"
}
]
}{
"type": "https://www.rfc-editor.org/rfc/rfc7231#section-6.5.1",
"title": "One or more validation errors occurred.",
"status": 400,
"instance": "/api/route",
"traceId": "0HMPNHL0JHL76:00000001",
"detail": "<string>",
"errors": [
{
"name": "Error or field name",
"reason": "Error reason",
"code": "<string>",
"severity": "<string>"
}
]
}{
"type": "https://www.rfc-editor.org/rfc/rfc7231#section-6.5.1",
"title": "One or more validation errors occurred.",
"status": 400,
"instance": "/api/route",
"traceId": "0HMPNHL0JHL76:00000001",
"detail": "<string>",
"errors": [
{
"name": "Error or field name",
"reason": "Error reason",
"code": "<string>",
"severity": "<string>"
}
]
}{
"type": "https://www.rfc-editor.org/rfc/rfc7231#section-6.5.1",
"title": "One or more validation errors occurred.",
"status": 400,
"instance": "/api/route",
"traceId": "0HMPNHL0JHL76:00000001",
"detail": "<string>",
"errors": [
{
"name": "Error or field name",
"reason": "Error reason",
"code": "<string>",
"severity": "<string>"
}
]
}{
"type": "https://www.rfc-editor.org/rfc/rfc7231#section-6.5.1",
"title": "One or more validation errors occurred.",
"status": 400,
"instance": "/api/route",
"traceId": "0HMPNHL0JHL76:00000001",
"detail": "<string>",
"errors": [
{
"name": "Error or field name",
"reason": "Error reason",
"code": "<string>",
"severity": "<string>"
}
]
}Authorizations
The access token received from the authorization server in the OAuth 2.0 flow.
Headers
Optional, client-generated key for deduplicating repeated write requests. A repeated request with the same key returns the originally recorded result instead of executing the effect again.
1 - 255The tenant ID for the target ERP instance.
Path Parameters
ID of the purchase order the position is added to. Der LieferantenBestellung Schlüssel.
"b45f6432-2462-4c6f-b00f-1d9d01000000"
Query Parameters
Indicates whether automatic workflows should be suppressed for this write. Defaults to false when omitted.
Body
Request model for CreatePurchaseOrderLineItem command endpoint. Route parameters bind from the route, query parameters from the query string, everything else from the body.
The article to order. It must already be assigned to the order's supplier; the API never auto-assigns. Kit articles, inactive articles and variation parents are rejected, exactly as on the create-order endpoint.
"b45f6432-2462-4c6f-b00f-1d9d01000000"
Ordered quantity; must be greater than zero.
Net purchase price per unit. Zero is allowed — it is the underlying column's own default — but a negative price is not.
VAT rate in percent, between 0 and 100 inclusive. A sanity bound only; specific rates are not whitelisted.
The supplier's own article number for this position. When omitted, resolved from the supplier's master data. A supplied value is used as given even when it differs from master data, because this is a free-text snapshot rather than a lookup key.
Expected delivery date of this position. When omitted, calculated from the article's (or, failing that, the supplier's) lead time in days, added to today.
Free-text note on the position, at most 2000 characters.
Response
The position was added. The body carries its new ID, which is all the caller needs to address it afterwards — the order-level consequences of the write (recalculated totals, open quantities) are visible through a subsequent read of the order.
Adds one article position to an existing purchase order. The order must be Open or Released — from InProgress onwards the position would already be part of a goods receipt. The article must already be assigned to the order's supplier; this endpoint never creates that assignment. Fields the caller omits are resolved from the supplier's master data, so the smallest useful request carries the article, the quantity, the net price and the VAT rate. - Response
Unique ID of the newly created line item.
"b45f6432-2462-4c6f-b00f-1d9d01000000"
Was this page helpful?