TimeToCargo

Migration workflow

Migrate references, identifiers, tracking data and notifications to TimeToCargo API v2

Follow this workflow alongside the guide for your provider. This page covers the shared steps, while each provider guide identifies the operations and fields to replace. Full request and response schemas are in the API reference.

1. Preserve references and ID mappings

One TimeToCargo record tracks one container, bill of lading (bl) or booking (bk) reference. A bill of lading or booking result can contain several containers. Former-provider IDs do not transfer. After creating tracking records, save a mapping between old and new IDs in your database.

ValuePurposeWhat to store
Container, bill of lading or booking referenceThe reference used to request carrier dataSave the reference, its type and carrier SCAC. These values are required for the request.
Former-provider IDA link to the former record in your applicationRetain the source ID and map it to the new tracking ID once the result is available.
data.task_idA temporary batch task IDKeep it until results are retrieved. Do not use it to update or stop tracking.
data.tracking_metadata.idA permanent tracking IDStore it alongside the source ID. The same ID appears as data.data[].id in the list response.
containers[].numberA container number within the resultStore it with the new tracking ID if your system manages individual containers within one document.

2. Configure authentication and request parameters

Create a key in your TimeToCargo account. The API base URL is https://tracking.timetocargo.com/v2. Send the key in the api_key query parameter of every request, including batch tasks and webhook management. The former provider's key cannot be reused. See authentication for access rules.

Use GET /v2/tracking for one reference and POST /v2/tracking/batch for several.

DataGET /v2/trackingPOST /v2/tracking/batch
API keyQuery parameter api_keyThe same api_key query parameter
ReferenceQuery parameter valueJSON body field tracked_items[].track_number.value
Reference typeQuery parameter type: container, bl or bkBody field tracked_items[].track_number.type with the same values
CarrierQuery parameter companyJSON body field tracked_items[].company
Route requestQuery parameter need_route=trueThe same need_route=true query parameter for the batch request
Tracking labelAfter obtaining the permanent ID, call PATCH /v2/shipments/{id} with noteObtain the permanent ID from the task result, then call the same PATCH

Reference, type and carrier are required. Find the carrier SCAC through GET /v2/companies and check support for the required reference type in cn, bl or bk. Map another provider's numeric ID or internal code to this directory first. Automatic carrier detection with company=AUTO is available only for type=container. Supply a SCAC for bills of lading and bookings.

3. Configure webhooks and retain history

If you need notifications from the first updates, create webhooks through POST /v2/webhooks before importing references. Webhooks are configured for the account, so do not send callback_url in each tracking request. Configure event_types, a new secret, signature verification and duplicate-delivery handling using the webhook guide.

GET /v2/webhook-notifications contains notification delivery records. Store received notifications in your system to maintain your own update archive. Export former-provider history, tags, last free pickup dates, fees, AIS measurements and custom fields separately.

4. Separate tracking initiation from stored data retrieval

ActionOperationRequired application change
Start tracking one reference and receive a responseGET /v2/trackingPass the reference, type and carrier. The request may activate tracking and consume a credit.
Start background processing for 1–500 referencesPOST /v2/tracking/batchSend the tracked_items array and save the returned data.task_id.
Retrieve a task resultGET /v2/tracking/batch?task_id=…Wait for data.status: "PROCESSED", then process each entry in data.results[].
Retrieve stored tracking recordsGET /v2/shipments?page=1&limit=50&status=ACTIVEIterate over data.data[] and fetch pages through data.meta.totalPages. Use status=ARCHIVED for archived records.
Retrieve a stored routeGET /v2/shipments?need_route=trueRead tracked_item.data.data.route_info from the selected record. Handle a possible null.
Edit a labelPATCH /v2/shipments/{id}Send note with up to 40 characters. An empty string clears it.
Stop tracking recordsDELETE /v2/shipmentsSend an array of new IDs in the body field shipmentIds. Check archiving and deletion rules in the lifecycle guide.

To retrieve one stored record, find its new ID in the /v2/shipments pages. There is no individual GET /v2/shipments/{id} or list filter by ID. Do not replace stored data retrieval with another /v2/tracking request: these operations have different purposes and credit rules.

For example, to request one container:

GET https://tracking.timetocargo.com/v2/tracking?api_key=YOUR_API_KEY&value=MSCU1234567&type=container&company=MSCU

The two batch responses

Send POST /v2/tracking/batch?api_key=YOUR_API_KEY with this body:

{
    "tracked_items": [
        {
            "track_number": {
                "type": "container",
                "value": "MSCU1234567"
            },
            "company": "MSCU"
        }
    ]
}

The creation response contains the task ID. Retrieve shipment data with a separate request:

POST /v2/tracking/batch response

{
    "success": true,
    "status": "OK",
    "data": {
        "task_id": "22222222-2222-4222-8222-222222222222"
    }
}

Then call GET /v2/tracking/batch?api_key=YOUR_API_KEY&task_id=22222222-2222-4222-8222-222222222222. The completed-task example below includes illustrative container data, events and a permanent tracking ID.

Task statuses are CREATED for waiting, HANDLING for processing, and PROCESSED for completed processing. After PROCESSED, check success and status for each entry in data.results[]. Task completion does not mean data was found for every reference.

Match each result to its submitted reference using results[].request.track_number. Save the permanent results[].data.tracking_metadata.id when data and tracking_metadata are not null. Results are retained for up to 6 hours. Save them after task completion; see batch tracking for a polling example with bounded retries.

5. Update response handling

In GET /v2/tracking, shipment data is under data. In GET /v2/shipments, first select a record from data.data[], then access its fields using the paths in the third column.

DataIn the GET /v2/tracking responseIn the selected data.data[] record
Shipment progressdata.shipment_statustracked_item.data.data.shipment_status
Carrier and main route pointsdata.summarytracked_item.data.data.summary
Containers and eventsdata.containers[].events[]tracked_item.data.data.containers[].events[]
Event locationsdata.locations[]tracked_item.data.data.locations[]
Terminalsdata.terminals[]tracked_item.data.data.terminals[]
Route and current positiondata.route_infotracked_item.data.data.route_info
Tracking IDdata.tracking_metadata.idid
Subscription statusdata.tracking_metadata.statusstatus: ACTIVE or ARCHIVED

Check the statuses separately:

  • success and status report the API request result. In a list, also check each record's tracked_item.data.success and tracked_item.data.status.
  • Batch data.status reports whether task processing has finished.
  • ACTIVE and ARCHIVED describe the tracking subscription.
  • shipment_status describes shipment progress, such as IN_TRANSIT or DELIVERED.

For events, use status_code, date and actual. Events run newest to oldest when every date is present; otherwise, the carrier’s order is preserved. Do not match events across providers by array index.

For example, CLL means loading at the origin port and CLT means transshipment loading. Resolve event.location to the corresponding id in locations, and event.terminal through terminals. actual=true means the event has occurred, while false means it is expected. A null value indicates missing information. Do not automatically treat a timestamp without a time zone as UTC.

Request route data with need_route=true. If shipment information is insufficient to construct a route, route_info may be null. Coordinates in route_info use [latitude, longitude] order. Reverse them to [longitude, latitude] for GeoJSON.

An empty result does not mean delivery. Distinguish missing data, carrier errors and completed shipments. Handle retries and HTTP 429 using the error guide, respecting Retry-After when present.

6. Validate with a small sample

  1. Export references, types, carriers and source ID relationships. You can use the TimeToCargo trial period to test the migration. Account for tracking allowance usage when submitting requests.
  2. Test a container, a bill of lading or booking with several containers, missing data and a completed shipment.
  3. Compare responses using your provider's examples. Check field paths, event codes, planned and actual dates, and coordinates. Predictions can differ between providers.
  4. Test pagination, individual batch failures, missing routes and duplicate webhook deliveries.
  5. Switch data retrieval and notifications to TimeToCargo. Keep your ID mapping and a way to restore the former integration. After validation, stop former subscriptions: TimeToCargo does not cancel them automatically.

Last updated on