pixiAddOrderLine
Adds a new order line for an item to an existing order, calculates prices and discounts, and returns the new order line ID or validation errors.
Adds one order line (Orderlines row) to the order PixiOrderNr.
1. Normalisation
ItemKey= 0 is treated as NULL andItemNrInt= '' as NULL.- An empty
Datebecomes the current date/time. - An empty
StatusbecomesNEW. - A NULL
UsePaymentStatusbecomes 0 and a NULLLocationIDbecomes001.
2. Validation All failed checks are collected, and each one adds an error row:
UsePaymentStatus= 1 together with aStatusother thanNEWis rejected.Statusmust be one ofNEW,ANG,HAL,FUT,STO,NLB.- If
ItemNrIntis given, the item is looked up byItemNrInt. The found key replacesItemKey. If no item matches, an error is raised. - If no error has occurred so far, the item must have an entry in
pixi.ItemCode. - A non-zero
Discount(voucher amount) requiresVoucherID. - If the order already has a line with a voucher, a different
VoucherIDis rejected. Only one voucher per order is allowed.
If any check fails, the error rows are returned and nothing is written.
3. Status from payment method
With UsePaymentStatus = 1, the line status is taken from Payments.IniOrderStatus of the payment method of the order's billing address.
4. Can lines be added?
pipiCanAddOrderlines checks whether the order still accepts new lines:
- For payment methods
K/C, all existing lines must be inNEW,ANG,HAL,MIN,OPH,BES,STOorNLB. - For other payment methods, no line may be in
EINorAUS.
Only if the result is 1 is the line created.
5. Header data
- Customer, addresses, order type, currency and the existing header values are read from the order.
OrderNrExternalis taken from the order header. If the header has none, the parameter is used. If that is also missing, a timestamp string is generated.Employeeis stored as<Employee> (API), or asAPIifEmployeeis not given.
6. Currency
If the setting MultiCurrencyEnabled is off, or the order has no exchange rate, the database currency is used with rate 1. Otherwise:
- Today's exchange rates are read from
pixi.ExchRate. - The database currency uses its rate source.
- The base currency of the order's exchange rate record uses the shop's
ExchRateSourceIDas source.
7. Prices
FullPrice(gross) and its net counterpart come from the parameter if it is non-zero.- Otherwise the item price is used: the price in the order currency first, then the base-currency price × rate, then the database-currency price × rate, else 0.
- For
B2Borders, theFullPriceparameter is interpreted as the net price, and the gross price is always taken from the item prices. ItemNameoverrides the item name.
8. Discount per line
FullPriceDiscountValueis used if it is given.- Otherwise
DiscountPercent% of the gross price (B2C) or of the net price (other order types) is used. - Otherwise the full price minus
DiscountedPriceis used. - Otherwise the discount is 0.
The same discount value is subtracted from both the gross and the net price to get Price and Price_Net.
9. Order header values
ShipCost,Discount,AddressRemarks,Verfahren,ProductandExtrasare taken from the parameters if they are non-empty or non-zero. Otherwise the existing header values are kept.- An existing voucher of the order always wins over
VoucherID.
10. Insert
The line is inserted via Pixi_InsertOrderline with these fixed values:
- source
I - line type
ORD - wait days 15
LocationIDas stock location and last order location
The call then returns a row with CanAdd = 1 and the new OrderlineId.
Notes
- No result when lines cannot be added: if
pipiCanAddOrderlinesreturns 0 or NULL, the call returns no rows at all. This happens when the order is not found or a line is already in a blocking status. Treat an empty response as "not added". - Duplicate error row: the check for
UsePaymentStatus= 1 withStatus≠NEWruns twice, so that error appears twice in the result. - Status not re-checked: a status taken from the payment method (
UsePaymentStatus= 1) is not validated against the allowed list. - Item price required: the item must have a price row in the database currency (inner join on
pixi.ItemPrice). Otherwise item data and prices are not filled and the line may be created without EAN or price. - Order header is overwritten:
Pixi_InsertOrderlineupdates the header columnsGiftMessage,ShipInstruct,Discount,Address_Remarks,Verfahren,Product,Extras,Shipdateand the tax rates.GiftMessagedefaults to '' and therefore overwrites an existing gift message.ShipInstructis set to '' andShipdateto NULL.
- Voucher creation: if the resulting
Discount> 0 and noVoucherrow with that ID exists, a voucher is created with shopGRMand the order currency. The expiry is computed withDATEADD(y, 1, …); datepartymeans day of year, so it lies one day after the order date. - Logging: if
OrderNrExternaldiffers from the header value, an entry is written toLogTable. - Transaction: the insert runs in a transaction inside
Pixi_InsertOrderline. - Order line ID: the new ID is read from a temp table that is filled by an
INSTEAD OFtrigger onOrderlines. The trigger is not attached. If no ID is returned,OrderlineIdis NULL althoughCanAdd= 1. - Reads: all reads use
NOLOCK. - Exchange rates: rates are looked up only for the current date. If no rate exists for today, converted prices become NULL.
Related calls
Tables used
| Parameter | Type | Default | Description |
|---|---|---|---|
PixiOrderNr
Required
|
int | – |
Pixi order number of the existing order. Example: |
ItemKey
|
int | NULL |
Internal item key. 0 is treated as NULL. It is replaced by the key found via Example: |
ItemNrInt
|
varchar(50) string |
NULL |
Shop item number used to look up the item. An empty string is treated as NULL. Example: |
Quantity
|
int | 1 |
Quantity of the order line. Example: |
ShipCost
|
money decimal |
0.0 |
Shipping cost of the line. If 0, the shipping cost of the order header is used. Example: |
LocationID
|
varchar(3) string |
001 |
Stock location ID of the line. NULL becomes Example: |
GiftMessage
|
varchar(8000) string |
– |
Gift message. It is written to the order header and overwrites the existing value, including with the default empty string. Example: |
DiscountPercent
|
numeric(6, 2) decimal |
NULL |
Line discount in percent of the full price (gross for B2C, net otherwise). Used only if Example: |
VoucherID
|
varchar(50) string |
NULL |
Voucher code. Required if Example: |
Discount
|
money decimal |
NULL |
Voucher amount for the order header. If NULL or 0, the existing header value is kept. If the resulting value is > 0, a voucher record is created if it does not exist yet. Example: |
AddressRemarks
|
varchar(255) string |
NULL |
Address remarks for the order header. If empty, the existing value is kept. Example: |
Verfahren
|
varchar(50) string |
NULL |
Value for the header field |
Product
|
varchar(50) string |
NULL |
Value for the header field |
Extras
|
varchar(50) string |
NULL |
Value for the header field |
Employee
|
varchar(50) string |
NULL |
Creating employee. It is stored with the suffix Example: |
Date
|
datetime dateTime |
NULL |
Creation date of the line ( Example: |
Status
|
varchar(3) string |
NULL |
Status of the new line. If empty, Allowed values
Example: |
UsePaymentStatus
|
bit boolean |
0 |
If 1, the line status is taken from the initial order status of the order's payment method. It cannot be combined with a Allowed values
Example: |
ItemNrExternal
|
varchar(50) string |
N |
External item number stored in the line. Example: |
FullPrice
|
money decimal |
NULL |
Full gross price before discount. For B2B orders this value is used as the net price. If NULL or 0, the item price is used. Example: |
FullPriceDiscountValue
|
money decimal |
NULL |
Absolute discount per unit. It has priority over Example: |
DiscountedPrice
|
money decimal |
NULL |
Price after discount. The discount is computed as the full price minus this value; used only if no other discount parameter is given. Example: |
ItemName
|
varchar(120) string |
NULL |
Item name for the line. If NULL, the item master name is used. Example: |
ItemSpecialNote
|
varchar(8000) string |
NULL |
Special note for the line ( Example: |
OrderNrExternal
|
varchar(50) string |
NULL |
External order number. It is used only if the order header has none; otherwise the header value wins. Without either, a timestamp string is generated. Example: |
DF_Type
|
varchar(1) string |
NULL |
Direct fulfillment type, stored in |
SerialNumber
|
varchar(50) string |
NULL |
Serial number stored in Example: |
Result set 1 · If at least one validation check fails (instead of the success result).
One row per failed check.
| Column | Type | Description |
|---|---|---|
CanAdd
|
bit boolean |
Always 0. |
OrderNr
|
int |
Requested order number. |
ErrorMessage
Nullable |
varchar(8000) string |
Error text. |
OrderlineId
Nullable |
int |
Always NULL. |
OrderNrExternal
Nullable |
string |
Always NULL. |
Result set 2 · If all checks pass and pipiCanAddOrderlines returns 1. If it returns 0 or NULL, no result set is returned.
One row with the created order line.
| Column | Type | Description |
|---|---|---|
CanAdd
|
bit boolean |
Always 1. |
OrderNr
|
int |
Pixi order number. |
ErrorMessage
Nullable |
varchar(8000) string |
Empty string. |
OrderlineId
Nullable |
int |
Key ( |
OrderNrExternal
Nullable |
varchar(50) string |
External order number stored in the new line. |
Response example
<SqlRowSet1>
<row>
<CanAdd>true</CanAdd>
<OrderNr>104532</OrderNr>
<ErrorMessage/>
<OrderlineId>887321</OrderlineId>
<OrderNrExternal>WEB-2024-000123</OrderNrExternal>
</row>
</SqlRowSet1>
| Status | Message | Cause |
|---|---|---|
| CanAdd = 0 | Error: Use either @Status or @UsePaymentStatus parameter. | `UsePaymentStatus` = 1 was combined with a `Status` other than `NEW`. Pass only one of them. This row is returned twice. |
| CanAdd = 0 | Error: Status {Status} is not allowed. | `Status` is not one of `NEW`, `ANG`, `HAL`, `FUT`, `STO`, `NLB`. |
| CanAdd = 0 | Error: Item with shop item number ({ItemNrInt}) not found. | No item with the given `ItemNrInt` exists. |
| CanAdd = 0 | Error: No item found. | No `ItemKey` was given, or the item has no entry in `pixi.ItemCode`. |
| CanAdd = 0 | Error: Parameter @VoucherId not provided for the parameter @Discount (Voucher Amount):{Discount} | `Discount` is not 0 but `VoucherID` is missing. |
| CanAdd = 0 | Error: A voucher with VoucherId: ("{ExistingVoucherID}") is already present on the order. Only one voucher per order is allowed. | The order already has a line with a different voucher. Pass the existing voucher ID or none. |
POST https://apigateway.descartes.com/tms/pixi/
Content-Type: text/xml; charset=utf-8
Authorization: Basic BASE64(USERNAME:PASSWORD)
<?xml version="1.0" encoding="UTF-8"?>
<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:ns1="https://apigateway.descartes.com/tms/pixi/">
<SOAP-ENV:Body>
<ns1:pixiAddOrderLine>
<PixiOrderNr>104532</PixiOrderNr>
<!-- <ItemKey>5821</ItemKey> -->
<!-- <ItemNrInt>ART-10045</ItemNrInt> -->
<!-- <Quantity>2</Quantity> -->
<!-- <ShipCost>4.90</ShipCost> -->
<!-- <LocationID>001</LocationID> -->
<!-- <GiftMessage>Happy Birthday!</GiftMessage> -->
<!-- <DiscountPercent>10.00</DiscountPercent> -->
<!-- <VoucherID>SUMMER2024</VoucherID> -->
<!-- <Discount>5.00</Discount> -->
<!-- <AddressRemarks>Please ring twice</AddressRemarks> -->
<!-- <Verfahren>?</Verfahren> -->
<!-- <Product>?</Product> -->
<!-- <Extras>?</Extras> -->
<!-- <Employee>jdoe</Employee> -->
<!-- <Date>2024-05-14T10:30:00</Date> -->
<!-- <Status>NEW</Status> -->
<!-- <UsePaymentStatus>0</UsePaymentStatus> -->
<!-- <ItemNrExternal>SHOP-4711</ItemNrExternal> -->
<!-- <FullPrice>29.90</FullPrice> -->
<!-- <FullPriceDiscountValue>3.00</FullPriceDiscountValue> -->
<!-- <DiscountedPrice>26.90</DiscountedPrice> -->
<!-- <ItemName>T-Shirt blue, size M</ItemName> -->
<!-- <ItemSpecialNote>Engraving: Anna</ItemSpecialNote> -->
<!-- <OrderNrExternal>WEB-2024-000123</OrderNrExternal> -->
<!-- <DF_Type>?</DF_Type> -->
<!-- <SerialNumber>SN-000981</SerialNumber> -->
</ns1:pixiAddOrderLine>
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>
curl -X POST 'https://apigateway.descartes.com/tms/pixi/' \
--user 'USERNAME:PASSWORD' \
--header 'Content-Type: text/xml; charset=utf-8' \
--data-binary @- <<'XML'
<?xml version="1.0" encoding="UTF-8"?>
<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:ns1="https://apigateway.descartes.com/tms/pixi/">
<SOAP-ENV:Body>
<ns1:pixiAddOrderLine>
<PixiOrderNr>104532</PixiOrderNr>
<!-- <ItemKey>5821</ItemKey> -->
<!-- <ItemNrInt>ART-10045</ItemNrInt> -->
<!-- <Quantity>2</Quantity> -->
<!-- <ShipCost>4.90</ShipCost> -->
<!-- <LocationID>001</LocationID> -->
<!-- <GiftMessage>Happy Birthday!</GiftMessage> -->
<!-- <DiscountPercent>10.00</DiscountPercent> -->
<!-- <VoucherID>SUMMER2024</VoucherID> -->
<!-- <Discount>5.00</Discount> -->
<!-- <AddressRemarks>Please ring twice</AddressRemarks> -->
<!-- <Verfahren>?</Verfahren> -->
<!-- <Product>?</Product> -->
<!-- <Extras>?</Extras> -->
<!-- <Employee>jdoe</Employee> -->
<!-- <Date>2024-05-14T10:30:00</Date> -->
<!-- <Status>NEW</Status> -->
<!-- <UsePaymentStatus>0</UsePaymentStatus> -->
<!-- <ItemNrExternal>SHOP-4711</ItemNrExternal> -->
<!-- <FullPrice>29.90</FullPrice> -->
<!-- <FullPriceDiscountValue>3.00</FullPriceDiscountValue> -->
<!-- <DiscountedPrice>26.90</DiscountedPrice> -->
<!-- <ItemName>T-Shirt blue, size M</ItemName> -->
<!-- <ItemSpecialNote>Engraving: Anna</ItemSpecialNote> -->
<!-- <OrderNrExternal>WEB-2024-000123</OrderNrExternal> -->
<!-- <DF_Type>?</DF_Type> -->
<!-- <SerialNumber>SN-000981</SerialNumber> -->
</ns1:pixiAddOrderLine>
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>
XML
<?php
$soapClient = new SoapClient(null, [
'login' => 'USERNAME',
'password' => 'PASSWORD',
'location' => 'https://apigateway.descartes.com/tms/pixi/',
'uri' => 'https://apigateway.descartes.com/tms/pixi/',
]);
$arguments = [
'PixiOrderNr' => '104532',
// 'ItemKey' => '5821',
// 'ItemNrInt' => 'ART-10045',
// 'Quantity' => '2',
// 'ShipCost' => '4.90',
// 'LocationID' => '001',
// 'GiftMessage' => 'Happy Birthday!',
// 'DiscountPercent' => '10.00',
// 'VoucherID' => 'SUMMER2024',
// 'Discount' => '5.00',
// 'AddressRemarks' => 'Please ring twice',
// 'Verfahren' => '?',
// 'Product' => '?',
// 'Extras' => '?',
// 'Employee' => 'jdoe',
// 'Date' => '2024-05-14T10:30:00',
// 'Status' => 'NEW',
// 'UsePaymentStatus' => '0',
// 'ItemNrExternal' => 'SHOP-4711',
// 'FullPrice' => '29.90',
// 'FullPriceDiscountValue' => '3.00',
// 'DiscountedPrice' => '26.90',
// 'ItemName' => 'T-Shirt blue, size M',
// 'ItemSpecialNote' => 'Engraving: Anna',
// 'OrderNrExternal' => 'WEB-2024-000123',
// 'DF_Type' => '?',
// 'SerialNumber' => 'SN-000981',
];
$soapArguments = [];
foreach ($arguments as $name => $value) {
$soapArguments[] = new SoapVar($value, XSD_STRING, '', '', $name);
}
$response = $soapClient->__soapCall('pixiAddOrderLine', $soapArguments);
- SQL object:
- dbo.pipiAddOrderLine