Step-by-Step Guide: SAP Integration with CubeMaster API

Learn how to consume the CubeMaster API (https://api.cubemaster.net/loads) using SAP with this detailed guide.

To use the CubeMaster API, you need an API key (TokenID) for authentication. Here's how to get started:

  1. Visit the CubeMaster website: https://cubemaster.net.
  2. Locate the "Sign In" option (typically found in the top-right corner).
  3. Fill out the registration form with your details (e.g., name, email, password, company information).
  4. After signing up, log in to your account dashboard.
  5. Navigate to the "Settings" - "Integration" section to generate your API key (TokenID).
  6. Generate an API key. Once generated, you’ll receive a unique TokenID (e.g., abc123xyz789). Copy this key and store it securely, as it will be used in the HTTP headers of your API requests.
  7. Copy the TokenID and store it securely.

Note: The TokenID will be used in the HTTP headers of your POST request for authentication.

For Beginners: What is a RESTful API? A RESTful API (Representational State Transfer) is a way for systems like SAP to communicate with external services (like CubeMaster) over the internet using standard HTTP methods (e.g., POST, GET). In this guide, we'll use the POST method to send data to https://api.cubemaster.net/loads and receive a response, all in a structured JSON format.

In SAP, orders and shipments data are stored in tables like VBAP (Sales Order Items) or LIKP (Delivery Document Header). You'll extract this data to build the API request:

  1. Log in to your SAP system using the SAP GUI.
  2. Go to transaction SE16 (Data Browser) or use a custom report via SE38.
  3. Access the relevant table (e.g., VBAP for order items) by entering the table name in the input field and pressing Enter.
  4. Filter the data using selection criteria (e.g., Sales Order Number in VBELN) to retrieve specific items like ITEM001, ITEM002, etc.
  5. Extract fields such as Material Number (MATNR), Quantity (KWMENG), and dimensions (if stored in custom fields or linked tables like MARA).
  6. For container details (e.g., 53FT-Intermodal), check tables like LIKP or a custom Z-table for shipment configurations.
  7. Save this data temporarily in an internal table in ABAP (e.g., lt_orders) for processing in the next step.

Example: For ITEM001, you might retrieve Length=72, Width=30, Height=75, Weight=1002.45, and Qty=16 from SAP.

Use ABAP to construct the JSON request payload based on the orders/shipments data from SAP:

  1. In SAP GUI, go to transaction SE38 to create or edit an ABAP program.
  2. Create a structure in the Data Dictionary (SE11) matching the CubeMaster API request format (e.g., ZLOAD_REQUEST with fields like Title, Cargoes, Containers).
  3. Map the SAP data to the JSON structure. For example, populate Cargoes with items from lt_orders and hardcode container details if not dynamic.
  4. Use the /UI2/CL_JSON class to serialize the ABAP structure into JSON format.

Request JSON:

{
    "Title": "New Mixed Truck Load",
    "Description": "Hello Web API",
    "Cargoes": [
        {
            "Name": "ITEM001",
            "Length": 72,
            "Width": 30,
            "Height": 75,
            "Weight": 1002.45,
            "OrientationsAllowed": "OrientationsAll",
            "TurnAllowedOnFloor": false,
            "Qty": 16,
            "ColorKnownName": "Brown"
        },
        {
            "Name": "ITEM002",
            "Length": 27.31,
            "Width": 37.5,
            "Height": 76.67,
            "Weight": 521.45,
            "OrientationsAllowed": "OrientationsAll",
            "TurnAllowedOnFloor": false,
            "Qty": 28,
            "ColorKnownName": "Aqua"
        },
        {
            "Name": "SKU0005",
            "Length": 27.31,
            "Width": 9.5,
            "Height": 75.67,
            "Weight": 501.45,
            "OrientationsAllowed": "OrientationsAll",
            "TurnAllowedOnFloor": true,
            "Qty": 24,
            "ColorKnownName": "Beige"
        },
        {
            "Name": "SKU0005",
            "Qty": 23
        },
        {
            "Name": "SKU0008",
            "Qty": 34
        }
    ],
    "Containers": [
        {
            "VehicleType": "Dry",
            "Name": "53FT-Intermodal",
            "Length": 630,
            "Width": 98,
            "Height": 106,
            "ColorKnownName": "Blue"
        }
    ],
    "Rules": {
        "IsWeightLimited": true,
        "IsSequenceUsed": false,
        "FillDirection": "FrontToRear",
        "CalculationType": "MixLoad"
    }
}

Configure the HTTP request in SAP with the TokenID in the headers:

  1. In your ABAP program (SE38), use the CL_HTTP_CLIENT class to create an HTTP client.
  2. Set the endpoint URL to https://api.cubemaster.net/loads.
  3. Add the TokenID to the request headers:
    • Header Key: Authorization
    • Header Value: TokenID abc123xyz789 (replace with your actual TokenID).
  4. Set the request method to POST using IF_HTTP_REQUEST->SET_METHOD( 'POST' ).
  5. Attach the JSON payload from Step 3 to the request body.
  6. Send the request using CL_HTTP_CLIENT->SEND and receive the response with CL_HTTP_CLIENT->RECEIVE.

Example Header:

Authorization: TokenID abc123xyz789

Process the response from CubeMaster to display or store results in SAP:

  1. Retrieve the response body as a string using CL_HTTP_CLIENT->RESPONSE->GET_CDATA( ).
  2. Deserialize the JSON response into an ABAP structure using /UI2/CL_JSON=>DESERIALIZE. Define a structure (e.g., ZLOAD_RESPONSE) in SE11 matching the response format.
  3. Check the status field:
    • If "succeed", proceed to extract data like loadSummary or filledContainers.
    • If an error (e.g., "InvalidCargoSize"), display an error message using MESSAGE.
  4. Display key metrics (e.g., cargoesLoaded, volumeUtilization) in an ALV Grid (transaction BCALV_GRID) or store them in a custom table (e.g., ZLOAD_RESULTS).
  5. Use the graphics.images URLs (e.g., path3DDiagram) to download and display load diagrams via SAP GUI's Picture Control.

Response JSON:

{
    "status": "succeed",
    "message": "Engine created. 5 cargoes. 1 empty containers. Calculation started. Calculation ended. The load built successfully. The load saved to the cloud database.",
    "calculationError": "InvalidCargoSize",
    "document": {
        "title": "New Mixed Truck Load",
        "description": "Hello Web API",
        "isShared": true,
        "isAutoSaved": true,
        "isPending": false,
        "calculationTimeInSeconds": 0.6152743,
        "processId": "",
        "batchId": "",
        "createdBy": "CHANG@LOGEN.CO.KR",
        "createdAt": "2023-02-11T01:17:01.7392204+09:00",
        "updatedAt": "0001-01-01T00:00:00"
    },
    "loadSummary": {
        "cargoesLoaded": 68,
        "piecesLoaded": 68,
        "cargoesLeft": 0,
        "piecesLeft": 57,
        "unitloadsLoaded": 0,
        "volumeLoaded": 5261723.4606,
        "weightLoaded": 42674.59999999999,
        "priceLoaded": 0,
        "containersLoaded": 1
    },
    "filledContainers": [
        {
            "name": "#1 53FT-Intermodal",
            "sequence": 1,
            "loadSummary": {
                "cargoesLoaded": 68,
                "piecesLoaded": 68,
                "unitloadsLoaded": 0,
                "volumeLoaded": 5261723.4606,
                "volumeUtilization": 80.39990374424703,
                "vollumeUtilizationToLoadHeight": 81.03441853085657,
                "floorLoaded": 57090.75,
                "floorUtilization": 92.46963070942662,
                "weightLoaded": 42674.59999999999,
                "weightTotal": 42674.59999999999,
                "weightUtilization": 0,
                "dimWeight": 39424.33734939759,
                "priceLoaded": 0,
                "pricetUtilization": 0,
                "cargoesPerLayer": 14,
                "layersPerUnitload": 0
            },
            "actualSize": {
                "length": 630,
                "width": 98,
                "height": 106
            },
            "loadSize": {
                "length": 625.6499999999999,
                "width": 97.5,
                "height": 105.17
            },
            "graphics": {
                "images": {
                    "path3DDiagram": "https://api.cubemaster.net/runtimes/b28413ca_51ed_44c9_b92e_13147363fd61.PNG",
                    "pathComposite": "https://api.cubemaster.net/runtimes/7eb09974_2f1d_41bc_9371_2002658dce07.PNG"
                }
            }
        }
    ]
}

Note: The full response is truncated here for brevity. Refer to the complete JSON for all fields.

Ensure the API integration works smoothly by monitoring and debugging:

  1. Use transaction SLG1 (Application Log) to log API requests and responses. Add custom log entries in your ABAP code with BAL_LOG_MSG_ADD.
  2. Enable tracing in transaction STAD (Statistics Display) to analyze the performance of HTTP calls.
  3. If errors occur (e.g., HTTP 401 Unauthorized), check the TokenID in the headers or validate the JSON payload using SE80's JSON editor.
  4. Use the SAP Gateway Client (/IWFND/GW_CLIENT) to simulate the POST request and inspect raw request/response data.
  5. Monitor the API response's message and calculationError fields to troubleshoot issues like InvalidCargoSize.

Tip: Save logs in a custom table (e.g., ZAPI_LOG) with fields like Timestamp, Request JSON, Response JSON, and Status for long-term analysis.