Documentation Index Fetch the complete documentation index at: https://mintlify.com/idempiere/idempiere/llms.txt
Use this file to discover all available pages before exploring further.
iDempiere’s REST API provides a modern, lightweight interface for integration. All SOAP services are automatically exposed as REST endpoints with support for both JSON and XML payloads.
Base URL
https://your-server:8443/ADInterface/services/rest
Content Types
The REST API supports both JSON and XML:
Content-Type : application/json
Accept : application/json
or
Content-Type : application/xml
Accept : application/xml
JSON is recommended for most modern applications due to smaller payload size and easier parsing.
ModelADService Endpoints
All ModelADService endpoints are available under /rest/model_adservice/.
Create Data
Create a new record in any iDempiere table.
cURL
JavaScript/Node.js
Python
curl -X POST https://localhost:8443/ADInterface/services/rest/model_adservice/create_data \
-H "Content-Type: application/json" \
-H "Accept: application/json" \
-d '{
"ModelCRUDRequest": {
"ModelCRUD": {
"serviceType": "CreateBPartner",
"TableName": "C_BPartner",
"RecordID": 0,
"Action": "Create",
"DataRow": {
"field": [
{
"@column": "Value",
"val": "CUST-001"
},
{
"@column": "Name",
"val": "New Customer Inc."
},
{
"@column": "IsCustomer",
"val": "Y"
},
{
"@column": "C_BP_Group_ID",
"val": "103"
}
]
}
},
"ADLoginRequest": {
"user": "WebService",
"pass": "WebService",
"lang": "en_US",
"ClientID": 11,
"RoleID": 50004,
"OrgID": 11,
"WarehouseID": 103,
"stage": 9
}
}
}'
The configured web service type name (e.g., “CreateBPartner”)
The database table name (e.g., “C_BPartner”, “C_Order”)
Set to 0 for create operations
Array of field objects with column name and value
StandardResponse.RecordID
The ID of the newly created record
Whether the operation failed
Error message if IsError is true
Read Data
Read a single record by ID.
curl -X POST https://localhost:8443/ADInterface/services/rest/model_adservice/read_data \
-H "Content-Type: application/json" \
-H "Accept: application/json" \
-d '{
"ModelCRUDRequest": {
"ModelCRUD": {
"serviceType": "ReadBPartner",
"TableName": "C_BPartner",
"RecordID": 118,
"Action": "Read"
},
"ADLoginRequest": {
"user": "WebService",
"pass": "WebService",
"lang": "en_US",
"ClientID": 11,
"RoleID": 50004,
"OrgID": 11,
"WarehouseID": 103,
"stage": 9
}
}
}'
The ID of the record to read
Update Data
Update an existing record.
curl -X POST https://localhost:8443/ADInterface/services/rest/model_adservice/update_data \
-H "Content-Type: application/json" \
-d '{
"ModelCRUDRequest": {
"ModelCRUD": {
"serviceType": "UpdateBPartner",
"TableName": "C_BPartner",
"RecordID": 118,
"Action": "Update",
"DataRow": {
"field": [
{
"@column": "Name",
"val": "Updated Customer Name"
},
{
"@column": "Description",
"val": "Customer description updated via REST API"
}
]
}
},
"ADLoginRequest": { ... }
}
}'
Delete Data
Delete a record by ID.
curl -X POST https://localhost:8443/ADInterface/services/rest/model_adservice/delete_data \
-H "Content-Type: application/json" \
-d '{
"ModelCRUDRequest": {
"ModelCRUD": {
"serviceType": "DeleteBPartner",
"TableName": "C_BPartner",
"RecordID": 118,
"Action": "Delete"
},
"ADLoginRequest": { ... }
}
}'
Delete operations are subject to database constraints. If the record has dependent records, the delete will fail.
Query Data
Query multiple records with filters, pagination, and sorting.
cURL with Filters
Filter by Field Values
curl -X POST https://localhost:8443/ADInterface/services/rest/model_adservice/query_data \
-H "Content-Type: application/json" \
-d '{
"ModelCRUDRequest": {
"ModelCRUD": {
"serviceType": "QueryBPartner",
"TableName": "C_BPartner",
"RecordID": 0,
"Filter": "IsCustomer=\u0027Y\u0027 AND Name LIKE \u0027A%\u0027",
"Action": "Read",
"Offset": 0,
"Limit": 50
},
"ADLoginRequest": { ... }
}
}'
SQL WHERE clause condition (without the WHERE keyword). Use standard SQL syntax with proper escaping.
Starting row for pagination (0-based)
Maximum number of rows to return
Alternative to Filter: specify field values to match
Create or Update Data
Create a new record if it doesn’t exist, or update if it does.
curl -X POST https://localhost:8443/ADInterface/services/rest/model_adservice/create_update_data \
-H "Content-Type: application/json" \
-d '{
"ModelCRUDRequest": {
"ModelCRUD": {
"serviceType": "CreateUpdateBPartner",
"TableName": "C_BPartner",
"RecordID": 0,
"recordIDVariable": "@C_BPartner_ID@",
"Action": "CreateUpdate",
"DataRow": {
"field": [
{
"@column": "Value",
"val": "CUST-001"
},
{
"@column": "Name",
"val": "Customer Name"
}
]
}
},
"ADLoginRequest": { ... }
}
}'
The system searches for an existing record matching the key fields. If found, it updates; otherwise, it creates a new record.
Run Process
Execute iDempiere processes and reports.
curl -X POST https://localhost:8443/ADInterface/services/rest/model_adservice/run_process \
-H "Content-Type: application/json" \
-d '{
"ModelRunProcessRequest": {
"ModelRunProcess": {
"serviceType": "RunInvoiceGenerate",
"@AD_Process_ID": 119,
"@AD_Menu_ID": 0,
"@AD_Record_ID": 0,
"ParamValues": {
"field": [
{
"@column": "C_DocType_ID",
"val": "1000000"
},
{
"@column": "DateInvoiced",
"val": "2024-03-01"
},
{
"@column": "C_BPartner_ID",
"val": "118"
}
]
}
},
"ADLoginRequest": { ... }
}
}'
The process ID to execute
Record ID for context (0 if not applicable)
Process parameters with column names and values
RunProcessResponse.IsError
Whether the process failed
RunProcessResponse.IsReport
Whether the process generated a report
RunProcessResponse.ReportFormat
Format of report data (pdf, html, xls, csv, etc.)
RunProcessResponse.Summary
Process execution summary message
Base64-encoded report data (if IsReport is true)
Set Document Action
Process documents with specific actions (Complete, Void, Close, etc.).
curl -X POST https://localhost:8443/ADInterface/services/rest/model_adservice/set_docaction \
-H "Content-Type: application/json" \
-d '{
"ModelSetDocActionRequest": {
"ModelSetDocAction": {
"serviceType": "CompleteOrder",
"tableName": "C_Order",
"recordID": 1000,
"docAction": "CO"
},
"ADLoginRequest": { ... }
}
}'
Document table name (C_Order, C_Invoice, etc.)
Document action code:
CO - Complete
CL - Close
VO - Void
RE - Reverse - Correct
RC - Reverse - Accrual
RA - Reactivate
PR - Post
Get List
Retrieve lookup lists and reference data.
curl -X POST https://localhost:8443/ADInterface/services/rest/model_adservice/get_list \
-H "Content-Type: application/json" \
-d '{
"ModelGetListRequest": {
"ModelGetList": {
"serviceType": "GetListSalesRegions",
"AD_Reference_ID": 144,
"Filter": ""
},
"ADLoginRequest": { ... }
}
}'
The reference ID (from AD_Reference table)
Optional filter to limit results
Composite Service Endpoints
Execute multiple operations atomically under /rest/composite_service/.
Composite Operation
curl -X POST https://localhost:8443/ADInterface/services/rest/composite_service/composite_operation \
-H "Content-Type: application/json" \
-d '{
"CompositeRequest": {
"ADLoginRequest": { ... },
"serviceType": "CompositeOrderEntry",
"operations": {
"operation": [
{
"@preCommit": false,
"@postCommit": false,
"TargetPort": "createData",
"ModelCRUD": {
"serviceType": "CreateOrder",
"TableName": "C_Order",
"RecordID": 0,
"Action": "Create",
"DataRow": {
"field": [
{ "@column": "C_BPartner_ID", "val": "118" },
{ "@column": "C_DocTypeTarget_ID", "val": "135" }
]
}
}
},
{
"@preCommit": false,
"@postCommit": false,
"TargetPort": "createData",
"ModelCRUD": {
"serviceType": "CreateOrderLine",
"TableName": "C_OrderLine",
"RecordID": 0,
"Action": "Create",
"DataRow": {
"field": [
{ "@column": "C_Order_ID", "val": "@C_Order.C_Order_ID@" },
{ "@column": "M_Product_ID", "val": "137" },
{ "@column": "QtyOrdered", "val": "5" }
]
}
}
},
{
"@preCommit": true,
"@postCommit": false,
"TargetPort": "setDocAction",
"ModelSetDocAction": {
"serviceType": "CompleteOrder",
"tableName": "C_Order",
"recordID": 0,
"recordIDVariable": "@C_Order.C_Order_ID@",
"docAction": "CO"
}
}
]
}
}
}'
Array of operations to execute in sequence
Operation type: createData, readData, updateData, deleteData, runProcess, setDocAction, createUpdateData
If true, commit transaction before this operation
If true, commit transaction after this operation
Use context variables like @TableName.ColumnName@ to reference values from previous operations in the composite request.
Field Types
Indicates the data type returned in responses:
ID - Integer identifier
String - Text value
Integer - Numeric integer
Number - Decimal number
YesNo - Boolean (Y/N)
Date - Date value
DateTime - Timestamp
List - List/lookup value
Dates and timestamps use ISO 8601 format:
Date: YYYY-MM-DD
DateTime: YYYY-MM-DD HH:MM:SS
Time: HH:MM:SS
Boolean Values
Use ‘Y’ for true and ‘N’ for false:
{ "@column" : "IsActive" , "val" : "Y" }
{ "@column" : "IsCustomer" , "val" : "N" }
Binary Data
Binary data (images, files) is Base64 encoded:
{ "@column" : "BinaryData" , "val" : "JVBERi0xLjQKJeLjz9..." }
Error Handling
Error Response Structure
{
"StandardResponse" : {
"@IsError" : true ,
"@IsRolledBack" : true ,
"@RecordID" : 0 ,
"Error" : "Invalid value for column C_BP_Group_ID: Foreign key constraint violation"
}
}
True if transaction was rolled back
Common HTTP Status Codes
200 OK - Request processed (check IsError flag)
400 Bad Request - Invalid JSON/XML payload
401 Unauthorized - Authentication failed
404 Not Found - Endpoint not found
500 Internal Server Error - Server error
Best Practices
Always Check IsError Flag
Even with HTTP 200, the operation may have failed. Always check the IsError field in the response. if ( data . StandardResponse . IsError ) {
console . error ( 'Operation failed:' , data . StandardResponse . Error );
}
Use Pagination for Large Datasets
Handle Binary Data Properly
When receiving binary data (reports, images), decode Base64: const pdfData = atob ( response . RunProcessResponse . Data );
const blob = new Blob ([ pdfData ], { type: 'application/pdf' });
Use Composite Service for Related Operations
Group related operations to ensure data consistency and reduce network overhead.
Network issues can occur. Implement exponential backoff for failed requests: from tenacity import retry, stop_after_attempt, wait_exponential
@retry ( stop = stop_after_attempt( 3 ), wait = wait_exponential( multiplier = 1 , min = 2 , max = 10 ))
def call_api ( payload ):
return requests.post(url, json = payload)