International Shipping Workflow

Follow Pedro, a small e-commerce business owner, as he ships his first international order from Mexico to the United States with proper customs documentation and HS code classification.

Meet Pedro

Pedro runs a small e-commerce business in Guadalajara, Mexico, selling handmade leather goods. He crafts beautiful wallets, belts, and bags that he sells online. Today, Pedro received his first international order—a customer in Miami, Florida wants to purchase a custom leather wallet. Pedro is excited but also nervous because he's never shipped internationally before. He needs to ensure the package arrives safely with all the proper customs documentation.

Business type

Small e-commerce business selling handmade leather goods

Challenge

First international shipment requiring customs documentation, HS codes, and commercial invoices

Solution

Use Envía APIs to classify products, validate addresses, get quotes with customs, and generate required documentation

The Journey

Pedro's international shipping workflow involves several important steps to ensure smooth customs clearance and delivery:

Step-by-Step Workflow

Step 1: Validate the Destination Address

What Pedro needs to do: Before shipping, Pedro wants to make sure the customer's address in Miami is valid. This prevents delivery issues and ensures accurate shipping quotes.

API Calls: Pedro can validate the destination address using the following endpoints:

From the Geocodes API:

  • Validate Zip Code - Verify postal codes and get city, state, and location details
  • Locate City - Find city information by city name and state, useful when postal codes aren't available or to validate city names

From the Queries API:

  • Get Address Structure - Get address structure requirements, required fields, and validation rules for a specific country (essential for international shipping to understand country-specific address formats)
  • Get States by Country - Retrieve all states or provinces for a country to validate state codes
  • Get State by Code - Get state details using its official code to verify state information

Pedro's customer provided the zip code 33139 in Miami, Florida. He uses the Validate Zip Code endpoint to validate it:

curl --request GET \
  --url "https://geocodes.envia.com/zipcode/US/33139" \
  --header "Authorization: Bearer $ENVIA_TOKEN"

Response example

{
  "meta": "zipcode",
  "data": {
    "postalCode": "33139",
    "city": "Miami Beach",
    "state": "FL",
    "country": "US"
  }
}
💡

Tip for Pedro: Validating addresses upfront helps prevent failed deliveries and ensures accurate shipping quotes. The response includes the correct city and state codes that Pedro will need for the shipping label.

Step 2: Classify the Product with HS Code

What Pedro needs to do: For international shipments, customs authorities require a Harmonized System (HS) code that classifies the product. Pedro needs to find the correct HS code for his leather wallet.

API Call: Classify HS Code from the Shipping API

Pedro describes his product: "Handmade leather wallet with multiple card slots and cash compartment"

curl --request POST \
  --url "https://api.envia.com/ship/utilities/classify-hscode" \
  --header "Authorization: Bearer $ENVIA_TOKEN" \
  --header "Content-Type: application/json" \
  --data '{
    "description": "Handmade leather wallet with multiple card slots and cash compartment",
    "shipToCountries": ["US"]
  }'

Response example

{
  "hsCode": "4202.31",
  "description": "Handbags, whether or not with shoulder strap, including those without handle, with outer surface of leather or of composition leather"
}
📋

Important for Pedro: The HS code returned (e.g., 4202.31 for leather wallets) will be needed for both the commercial invoice and the shipping label. Pedro should save this code for the next steps.

Step 3: Check Available Carriers

What Pedro needs to do: Pedro wants to see which carriers can ship from Mexico to the United States, so he can choose the best option for his customer.

💡

Note: If Pedro already knows which carrier he wants to use (e.g., he always uses DHL for international shipments), he can skip this step and proceed directly to getting a quote with that carrier.

API Call: Get Available Carriers from the Queries API

curl --request GET \
  --url "https://queries.envia.com/carriers?countryCode=MX&shipmentType=1" \
  --header "Authorization: Bearer $ENVIA_TOKEN"

Response example

{
  "meta": "carriers",
  "data": [
    {
      "carrier": "dhl",
      "name": "DHL"
    },
    {
      "carrier": "fedex",
      "name": "FedEx"
    },
    {
      "carrier": "ups",
      "name": "UPS"
    }
  ]
}

Pedro discovers that DHL, FedEx, and UPS all support shipping from Mexico to the United States. He decides to get quotes from DHL.

Step 4: Get Quote with Customs Information

What Pedro needs to do: Now Pedro needs to get a shipping quote. Since this is an international shipment, he must include customs settings to get accurate pricing that includes duties and taxes. Pedro wants to use "Envia Guaranteed" so his customer knows the exact total cost upfront with no surprises.

API Call: Quote Shipments from the Shipping API

curl --request POST \
  --url "https://api.envia.com/ship/rate/" \
  --header "Authorization: Bearer $ENVIA_TOKEN" \
  --header "Content-Type: application/json" \
  --data '{
    "origin": {
      "name": "Pedro Martinez",
      "company": "Pedro Leather Goods",
      "phone": "+52 3331234567",
      "email": "[email protected]",
      "street": "Av. Revolucion 123",
      "city": "Guadalajara",
      "state": "JA",
      "country": "MX",
      "postalCode": "44100"
    },
    "destination": {
      "name": "John Smith",
      "phone": "+1 3055551234",
      "street": "123 Ocean Drive",
      "city": "Miami Beach",
      "state": "FL",
      "country": "US",
      "postalCode": "33139"
    },
    "packages": [
      {
        "type": "box",
        "content": "Leather wallet",
        "amount": 1,
        "declaredValue": 85,
        "weight": 0.2,
        "weightUnit": "KG",
        "lengthUnit": "CM",
        "dimensions": {
          "length": 12,
          "width": 9,
          "height": 2
        },
        "items": [
          {
            "description": "Handmade leather wallet",
            "hsCode": "4202.31",
            "quantity": 1,
            "price": 85,
            "countryOfManufacture": "MX"
          }
        ]
      }
    ],
    "shipment": {
      "type": 1,
      "carrier": "dhl"
    },
    "customsSettings": {
      "dutiesPaymentEntity": "envia_guaranteed",
      "exportReason": "sale"
    }
  }'

Response example

{
  "meta": "rate",
  "data": [
    {
      "carrier": "dhl",
      "service": "int_express",
      "serviceDescription": "DHL Express International",
      "deliveryEstimate": "2-3 business days",
      "totalPrice": "245.80",
      "currency": "USD",
      "shippingCost": "185.50",
      "dutiesAndTaxes": "60.30"
    }
  ]
}

Pedro learns: By using "dutiesPaymentEntity": "envia_guaranteed", Pedro gets a quote that includes all duties and taxes upfront. This means his customer in Miami will know the exact total cost with no surprise charges at delivery. The quote response includes the total cost (shipping + duties + taxes) so Pedro can show his customer the complete price.

Step 5: Create Commercial Invoice

What Pedro needs to do: Before creating the shipping label, Pedro needs to generate a commercial invoice. This document is required by customs authorities and includes all product details, values, and HS codes.

API Call: Create Commercial Invoice from the Shipping API

curl --request POST \
  --url "https://api.envia.com/ship/commercial-invoice/" \
  --header "Authorization: Bearer $ENVIA_TOKEN" \
  --header "Content-Type: application/json" \
  --data '{
    "shipper": {
      "name": "Pedro Martinez",
      "company": "Pedro Leather Goods",
      "phone": "+52 3331234567",
      "email": "[email protected]",
      "street": "Av. Revolucion 123",
      "city": "Guadalajara",
      "state": "JA",
      "country": "MX",
      "postalCode": "44100"
    },
    "recipient": {
      "name": "John Smith",
      "phone": "+1 3055551234",
      "email": "[email protected]",
      "street": "123 Ocean Drive",
      "city": "Miami Beach",
      "state": "FL",
      "country": "US",
      "postalCode": "33139"
    },
    "items": [
      {
        "description": "Handmade leather wallet with multiple card slots",
        "hsCode": "4202.31",
        "quantity": 1,
        "price": 85,
        "currency": "USD",
        "countryOfManufacture": "MX"
      }
    ],
    "exportReason": "sale",
    "terms": "DDP"
  }'

Response example

{
  "meta": "commercial_invoice",
  "data": {
    "invoiceId": "INV-2025-001",
    "invoiceUrl": "https://files.envia.com/invoices/INV-2025-001.pdf",
    "invoiceNumber": "CI-2025-001"
  }
}
📄

Important for Pedro: The commercial invoice PDF should be printed and attached to the package, or the invoice reference should be included when creating the shipping label. Some carriers require the commercial invoice to be physically attached to the shipment.

Step 6: Create Shipping Label

What Pedro needs to do: Now Pedro can create the actual shipping label. He'll use the service code from the quote he received earlier, along with all the customs information.

API Call: Create Shipping Label from the Shipping API

curl --request POST \
  --url "https://api.envia.com/ship/create/" \
  --header "Authorization: Bearer $ENVIA_TOKEN" \
  --header "Content-Type: application/json" \
  --data '{
    "origin": {
      "name": "Pedro Martinez",
      "company": "Pedro Leather Goods",
      "phone": "+52 3331234567",
      "email": "[email protected]",
      "street": "Av. Revolucion 123",
      "city": "Guadalajara",
      "state": "JA",
      "country": "MX",
      "postalCode": "44100"
    },
    "destination": {
      "name": "John Smith",
      "phone": "+1 3055551234",
      "email": "[email protected]",
      "street": "123 Ocean Drive",
      "city": "Miami Beach",
      "state": "FL",
      "country": "US",
      "postalCode": "33139"
    },
    "packages": [
      {
        "type": "box",
        "content": "Leather wallet",
        "amount": 1,
        "declaredValue": 85,
        "weight": 0.2,
        "weightUnit": "KG",
        "lengthUnit": "CM",
        "dimensions": {
          "length": 12,
          "width": 9,
          "height": 2
        },
        "items": [
          {
            "description": "Handmade leather wallet",
            "hsCode": "4202.31",
            "quantity": 1,
            "price": 85,
            "countryOfManufacture": "MX"
          }
        ]
      }
    ],
    "shipment": {
      "type": 1,
      "carrier": "dhl",
      "service": "int_express"
    },
    "customsSettings": {
      "dutiesPaymentEntity": "envia_guaranteed",
      "exportReason": "sale"
    }
  }'

Response example

{
  "meta": "generate",
  "data": [
    {
      "carrier": "dhl",
      "service": "int_express",
      "shipmentId": 987654,
      "trackingNumber": "1234567890",
      "trackUrl": "https://tracking.envia.com/1234567890",
      "label": "https://files.envia.com/labels/1234567890.pdf",
      "totalPrice": 245.8,
      "currency": "USD"
    }
  ]
}
🎉

Success! Pedro has successfully created his first international shipping label. The response includes a tracking number that he can share with his customer, and a PDF label that he can print and attach to the package.

Step 7: Track the Shipment

What Pedro needs to do: Pedro wants to monitor his package's journey and keep his customer informed. He'll use the tracking number from the label he just created.

API Call: Track Shipments from the Shipping API

curl --request GET \
  --url "https://api.envia.com/ship/tracking?trackingNumbers=1234567890&carrier=dhl" \
  --header "Authorization: Bearer $ENVIA_TOKEN"

Response example

{
  "meta": "track",
  "data": [
    {
      "trackingNumber": "1234567890",
      "status": "In transit",
      "carrier": "dhl",
      "events": [
        {
          "timestamp": "2025-01-27T12:30:00Z",
          "location": "Guadalajara, MX",
          "description": "Shipment picked up"
        },
        {
          "timestamp": "2025-01-27T18:45:00Z",
          "location": "Mexico City, MX",
          "description": "In transit to destination"
        }
      ]
    }
  ]
}

What Pedro Learned

Through this journey, Pedro discovered several important things about international shipping:

  1. Address validation is crucial - Validating the destination address upfront prevents delivery issues
  2. HS codes are required - Products need proper classification for customs clearance
  3. Envia Guaranteed simplifies pricing - His customers know the exact total cost with no surprises
  4. Commercial invoices are mandatory - International shipments require proper customs documentation
  5. The workflow is straightforward - With Envia's APIs, international shipping is manageable even for small businesses

Pedro's customer in Miami received the package on time with all proper documentation, and Pedro is now confident he can handle more international orders!

Related Resources