python - 如何在 python-fedex 中为国际货件添加海关值(value)?

标签 python soap fedex

我使用 python-fedex 模块作为 FedEx SOAP API 的轻型包装器。作为此过程的一部分,我试图设置一个国际 cargo 的基本示例,但我遇到了以下错误消息:

fedex.base_service.FedexError:需要海关值(value)。 (错误代码:2033)

我相信我需要添加我作为商品运送的产品,包括。他们的海关值(value) - 但我很难让它发挥作用。我找到了 this link 并提供了一些指导(来自 C#),但我无法让它在 Python 中工作。任何意见都将受到赞赏!

我的代码如下:


# !/usr/bin/env python
"""
This example shows how to create a shipment and generate a waybill as output. The variables populated below
represents the minimum required values. You will need to fill all of these, or
risk seeing a SchemaValidationError exception thrown.

Near the bottom of the module, you'll see some different ways to handle the
label data that is returned with the reply.
"""

import logging
import binascii
import datetime
import sys, os

from example_config import CONFIG_OBJ

from fedex.services.ship_service import FedexProcessShipmentRequest


# What kind of file do you want this example to generate?
# Valid choices for this example are PDF, PNG
GENERATE_IMAGE_TYPE = 'PDF'

# Un-comment to see the response from Fedex printed in stdout.
logging.basicConfig(stream=sys.stdout, level=logging.INFO)

# This is the object that will be handling our shipment request.
# We're using the FedexConfig object from example_config.py in this dir.
customer_transaction_id = "*** ShipService Request v17 using Python ***"  # Optional transaction_id
shipment = FedexProcessShipmentRequest(CONFIG_OBJ, customer_transaction_id=customer_transaction_id)

# This is very generalized, top-level information.
# REGULAR_PICKUP, REQUEST_COURIER, DROP_BOX, BUSINESS_SERVICE_CENTER or STATION
shipment.RequestedShipment.DropoffType = 'BUSINESS_SERVICE_CENTER'

# See page 355 in WS_ShipService.pdf for a full list. Here are the common ones:
# STANDARD_OVERNIGHT, PRIORITY_OVERNIGHT, FEDEX_GROUND, FEDEX_EXPRESS_SAVER,
# FEDEX_2_DAY, INTERNATIONAL_PRIORITY, SAME_DAY, INTERNATIONAL_ECONOMY
shipment.RequestedShipment.ServiceType = 'INTERNATIONAL_PRIORITY'

# What kind of package this will be shipped in.
# FEDEX_BOX, FEDEX_PAK, FEDEX_TUBE, YOUR_PACKAGING, FEDEX_ENVELOPE
shipment.RequestedShipment.PackagingType = 'FEDEX_ENVELOPE'

# Shipper contact info.
shipment.RequestedShipment.Shipper.Contact.PersonName = 'Shipper Name'
shipment.RequestedShipment.Shipper.Contact.CompanyName = 'Shipper Company'
shipment.RequestedShipment.Shipper.Contact.PhoneNumber = '004512345678'

# Shipper address.
shipment.RequestedShipment.Shipper.Address.StreetLines = ['Shipper Address']
shipment.RequestedShipment.Shipper.Address.City = 'City'
shipment.RequestedShipment.Shipper.Address.StateOrProvinceCode = ''
shipment.RequestedShipment.Shipper.Address.PostalCode = '8270'
shipment.RequestedShipment.Shipper.Address.CountryCode = 'DK'
shipment.RequestedShipment.Shipper.Address.Residential = False

# Recipient contact info.
shipment.RequestedShipment.Recipient.Contact.PersonName = 'US customer X'
shipment.RequestedShipment.Recipient.Contact.CompanyName = 'US company X'
shipment.RequestedShipment.Recipient.Contact.PhoneNumber = '0123456789'

# Recipient address
shipment.RequestedShipment.Recipient.Address.StreetLines = ['668 MURRAY AVE SE']
shipment.RequestedShipment.Recipient.Address.City = 'ROANOKE'
shipment.RequestedShipment.Recipient.Address.StateOrProvinceCode = 'VA'
shipment.RequestedShipment.Recipient.Address.PostalCode = '24013'
shipment.RequestedShipment.Recipient.Address.CountryCode = 'US'
# This is needed to ensure an accurate rate quote with the response. Use AddressValidation to get ResidentialStatus
shipment.RequestedShipment.Recipient.Address.Residential = False
shipment.RequestedShipment.EdtRequestType = 'NONE'

# Senders account information
shipment.RequestedShipment.ShippingChargesPayment.Payor.ResponsibleParty.AccountNumber = CONFIG_OBJ.account_number

# Who pays for the shipment?
# RECIPIENT, SENDER or THIRD_PARTY
shipment.RequestedShipment.ShippingChargesPayment.PaymentType = 'SENDER'

# Specifies the label type to be returned.
# LABEL_DATA_ONLY or COMMON2D
shipment.RequestedShipment.LabelSpecification.LabelFormatType = 'COMMON2D'

# Specifies which format the label file will be sent to you in.
# DPL, EPL2, PDF, PNG, ZPLII
shipment.RequestedShipment.LabelSpecification.ImageType = GENERATE_IMAGE_TYPE

# To use doctab stocks, you must change ImageType above to one of the
# label printer formats (ZPLII, EPL2, DPL).
# See documentation for paper types, there quite a few.
shipment.RequestedShipment.LabelSpecification.LabelStockType = 'PAPER_7X4.75'

# This indicates if the top or bottom of the label comes out of the
# printer first.
# BOTTOM_EDGE_OF_TEXT_FIRST or TOP_EDGE_OF_TEXT_FIRST
# Timestamp in YYYY-MM-DDThh:mm:ss format, e.g. 2002-05-30T09:00:00
shipment.RequestedShipment.ShipTimestamp = datetime.datetime.now().replace(microsecond=0).isoformat()

# BOTTOM_EDGE_OF_TEXT_FIRST, TOP_EDGE_OF_TEXT_FIRST
shipment.RequestedShipment.LabelSpecification.LabelPrintingOrientation = 'TOP_EDGE_OF_TEXT_FIRST'

# Delete the flags we don't want.
# Can be SHIPPING_LABEL_FIRST, SHIPPING_LABEL_LAST or delete
if hasattr(shipment.RequestedShipment.LabelSpecification, 'LabelOrder'):
    del shipment.RequestedShipment.LabelSpecification.LabelOrder  # Delete, not using.

# Create Weight, in pounds.
package1_weight = shipment.create_wsdl_object_of_type('Weight')
package1_weight.Value = 1.0
package1_weight.Units = "LB"

# Create PackageLineItem
package1 = shipment.create_wsdl_object_of_type('RequestedPackageLineItem')
# BAG, BARREL, BASKET, BOX, BUCKET, BUNDLE, CARTON, CASE, CONTAINER, ENVELOPE etc..
package1.PhysicalPackaging = 'ENVELOPE'
package1.Weight = package1_weight


# Add a signature option for the package using SpecialServicesRequested or comment out.
# SpecialServiceTypes can be APPOINTMENT_DELIVERY, COD, DANGEROUS_GOODS, DRY_ICE, SIGNATURE_OPTION etc..
package1.SpecialServicesRequested.SpecialServiceTypes = 'SIGNATURE_OPTION'
# SignatureOptionType can be ADULT, DIRECT, INDIRECT, NO_SIGNATURE_REQUIRED, SERVICE_DEFAULT
package1.SpecialServicesRequested.SignatureOptionDetail.OptionType = 'SERVICE_DEFAULT'


# This adds the RequestedPackageLineItem WSDL object to the shipment. It
# increments the package count and total weight of the shipment for you.
shipment.add_package(package1)


# If you want to make sure that all of your entered details are valid, you
# can call this and parse it just like you would via send_request(). If
# shipment.response.HighestSeverity == "SUCCESS", your shipment is valid.
# print(shipment.send_validation_request())

# Fires off the request, sets the 'response' attribute on the object.
shipment.send_request()

最佳答案

我在下面添加了完整的国际运输示例,它解决了这个问题:

"""
This example shows how to create an international shipment and generate a waybill as output.
The example takes outset in a real practical use case, where electronic trade documents are
used and an existing PDF commercial invoice is added along with product descriptions via ETD.
Further, it adds event notifications to allow for emails to be sent to the end recipient.
The script is comprised of a FedExLabelHelper class with all core functions, and a use case
example with minimal dummy data
"""
from example_config import CONFIG_OBJ
from pathlib import Path
import binascii
import datetime
from fedex.services.ship_service import FedexProcessShipmentRequest

# ----------------------------------------------------
# FedEx class for creating shipments
class FedexLabelHelper:
    mCommodities = []

    def __init__(self):
        pass

    # ----------------------------------------------------
    # set overall shipment configuration
    def setShipmentConfig(
        self,
        CONFIG_OBJ,
        invoice_info,
        cust_tran_id="*** ShipService Request v17 using Python ***",
        dropoffType="BUSINESS_SERVICE_CENTER",
        shippingPaymentType="SENDER",
        labelFormatType="COMMON2D",
        labelSpecificationImageType="PDF",
        labelSpecificationStockType="PAPER_7X4.75",
        labelPrintingOrientation="TOP_EDGE_OF_TEXT_FIRST",
        LabelOrder="SHIPPING_LABEL_FIRST",
    ):
        self.invoice_info = invoice_info
        self.dropoffType = dropoffType
        self.serviceType = "INTERNATIONAL_PRIORITY" if invoice_info["ShippingExpress"] == True else "INTERNATIONAL_ECONOMY"
        self.mCommodities.clear()
        self.CONFIG_OBJ = CONFIG_OBJ
        self.shipment = FedexProcessShipmentRequest(CONFIG_OBJ, customer_transaction_id=cust_tran_id)

        self.shipment.RequestedShipment.DropoffType = dropoffType
        self.shipment.RequestedShipment.ServiceType = self.serviceType
        self.shipment.RequestedShipment.ShippingChargesPayment.Payor.ResponsibleParty.AccountNumber = CONFIG_OBJ.account_number
        self.shipment.RequestedShipment.ShippingChargesPayment.Payor.ResponsibleParty.Address.CountryCode = "DK"
        self.shipment.RequestedShipment.ShippingChargesPayment.PaymentType = shippingPaymentType

        labelSpecification = self.shipment.create_wsdl_object_of_type("LabelSpecification")
        labelSpecification.LabelFormatType = labelFormatType
        labelSpecification.LabelStockType = labelSpecificationStockType
        labelSpecification.ImageType = labelSpecificationImageType
        labelSpecification.LabelOrder = LabelOrder
        labelSpecification.LabelPrintingOrientation = labelPrintingOrientation
        self.shipment.RequestedShipment.LabelSpecification = labelSpecification

    # ----------------------------------------------------
    # set sender information
    def setSenderInfo(self, sender):

        self.shipment.RequestedShipment.Shipper.Contact.PersonName = sender["Name"]
        self.shipment.RequestedShipment.Shipper.Contact.CompanyName = sender["Company"]
        self.shipment.RequestedShipment.Shipper.Contact.PhoneNumber = sender["Phone"]
        self.shipment.RequestedShipment.Shipper.Contact.EMailAddress = sender["Email"]
        self.shipment.RequestedShipment.Shipper.Address.StreetLines = sender["Address"]
        self.shipment.RequestedShipment.Shipper.Address.City = sender["City"]
        self.shipment.RequestedShipment.Shipper.Address.StateOrProvinceCode = sender["Region"]
        self.shipment.RequestedShipment.Shipper.Address.PostalCode = sender["Zip"]
        self.shipment.RequestedShipment.Shipper.Address.CountryCode = sender["CountryCode"]
        self.shipment.RequestedShipment.Shipper.Address.Residential = sender["Residential"]

        ti = self.shipment.create_wsdl_object_of_type("TaxpayerIdentification")
        ti.Number = sender["VAT"]
        ti.TinType = "BUSINESS_NATIONAL"
        self.shipment.RequestedShipment.Shipper.Tins = ti

    # ----------------------------------------------------
    # upload all documents (invoice and product information)
    def upload_all_documents(self):
        doc_ids = []
        doc_ids.append(self.upload_document(self.invoice_info["InvoicePath"], "COMMERCIAL_INVOICE"))

        for pdf in self.invoice_info["Pdfs"]:
            doc_ids.append(self.upload_document(pdf, "OTHER"))

        return doc_ids

    # ----------------------------------------------------
    # function for uploading documents as electronic trade documents and getting the response doc IDs
    def upload_document(self, path, type):
        from fedex.services.document_service import FedexDocumentServiceRequest

        # specify prefix for use in attachment naming
        if type == "COMMERCIAL_INVOICE":
            prefix = "invoice_"
        else:
            prefix = "product_description_"

        uploadRequest = FedexDocumentServiceRequest(self.CONFIG_OBJ)
        uploadRequest.OriginCountryCode = "DK"
        uploadRequest.DestinationCountryCode = self.shipment.RequestedShipment.Recipient.Address.CountryCode
        uploadRequest.Usage = "ELECTRONIC_TRADE_DOCUMENTS"

        clientdetails = uploadRequest.create_wsdl_object_of_type("ClientDetail")
        clientdetails.AccountNumber = self.CONFIG_OBJ.account_number
        clientdetails.MeterNumber = self.CONFIG_OBJ.meter_number
        uploadRequest.ClientDetail = clientdetails

        webAuthDetails = uploadRequest.create_wsdl_object_of_type("WebAuthenticationDetail")
        webAuthDetails.ParentCredential.Key = self.CONFIG_OBJ.key
        webAuthDetails.ParentCredential.Password = self.CONFIG_OBJ.password
        webAuthDetails.UserCredential.Key = self.CONFIG_OBJ.key
        webAuthDetails.UserCredential.Password = self.CONFIG_OBJ.password
        uploadRequest.WebAuthenticationDetail = webAuthDetails

        docdetails = uploadRequest.create_wsdl_object_of_type("UploadDocumentDetail")
        docdetails.LineNumber = 1
        docdetails.DocumentType = type
        docdetails.FileName = prefix + path
        fileContent = open(path, "rb").read()
        fileBase64 = binascii.b2a_base64(fileContent)
        docdetails.DocumentContent = fileBase64.decode("cp1250")
        uploadRequest.Documents = docdetails

        uploadRequest.send_request()

        doc_id = uploadRequest.response.DocumentStatuses[0].DocumentId

        return doc_id

    # ----------------------------------------------------
    # set recipient information
    def setRecipientInfo(self, recipient):
        self.shipment.RequestedShipment.Recipient.Contact.PersonName = recipient["Name"]
        self.shipment.RequestedShipment.Recipient.Contact.CompanyName = recipient["Company"]
        self.shipment.RequestedShipment.Recipient.Contact.PhoneNumber = recipient["Phone"]
        self.shipment.RequestedShipment.Recipient.Contact.EMailAddress = recipient["Email"]
        self.shipment.RequestedShipment.Recipient.Address.StreetLines = recipient["Address"]
        self.shipment.RequestedShipment.Recipient.Address.City = recipient["City"]
        self.shipment.RequestedShipment.Recipient.Address.StateOrProvinceCode = recipient["Region"]
        self.shipment.RequestedShipment.Recipient.Address.PostalCode = recipient["Zip"]
        self.shipment.RequestedShipment.Recipient.Address.CountryCode = recipient["CountryCode"]
        self.shipment.RequestedShipment.Recipient.Address.Residential = recipient["Residential"]

        ti = self.shipment.create_wsdl_object_of_type("TaxpayerIdentification")
        ti.Number = recipient["VAT"]
        ti.TinType = "BUSINESS_NATIONAL"
        self.shipment.RequestedShipment.Recipient.Tins = ti

    # ----------------------------------------------------
    # add "commercial invoice" reference as the only commodity
    def add_ci_commodity(self):

        self.addCommodity(
            cCustomsValueAmnt=self.invoice_info["Value"],
            cCustomsValueCurrency=self.invoice_info["Currency"],
            cWeightValue=self.invoice_info["Weight"],
            cDescription="See attached commercial invoice",
            cQuantity=self.invoice_info["Quantity"],
            cExportLicenseNumber=self.shipment.RequestedShipment.Shipper.Tins.Number,
            cPartNumber=1,
        )

    # ----------------------------------------------------
    # add commodity to shipment (for now, just add 1 commodity to refer to attached CI)
    def addCommodity(
        self, cCustomsValueAmnt, cCustomsValueCurrency, cWeightValue, cDescription, cQuantity, cExportLicenseNumber, cPartNumber,
    ):

        commodity = self.shipment.create_wsdl_object_of_type("Commodity")
        commodity.NumberOfPieces = str(cQuantity)
        commodity.Description = cDescription
        commodity.Quantity = cQuantity
        commodity.QuantityUnits = "EA"
        commodity.ExportLicenseNumber = cExportLicenseNumber
        commodity.PartNumber = cPartNumber
        commodity.CountryOfManufacture = "DK"

        mCustomsValue = self.shipment.create_wsdl_object_of_type("Money")
        mCustomsValue.Amount = cCustomsValueAmnt
        mCustomsValue.Currency = cCustomsValueCurrency
        commodity.CustomsValue = mCustomsValue

        commodity_weight = self.shipment.create_wsdl_object_of_type("Weight")
        commodity_weight.Value = cWeightValue
        commodity_weight.Units = "KG"
        commodity.Weight = commodity_weight

        munitPrice = self.shipment.create_wsdl_object_of_type("Money")
        munitPrice.Amount = float(round((cCustomsValueAmnt / cQuantity), 2))
        munitPrice.Currency = cCustomsValueCurrency
        commodity.UnitPrice = munitPrice

        self.mCommodities.append(commodity)

    # ----------------------------------------------------
    # add package to shipment
    def set_packaging_info(self):
        weight = self.invoice_info["Weight"]

        type = "BOX" if weight > 0.5 else "ENVELOPE"
        weight_final = float(round(weight + 0.2, 2)) if weight > 0.5 else 0.4

        self.addShippingPackage(packageWeight=weight_final, physicalPackagingType=type, packagingType=f"FEDEX_{type}")

    # ----------------------------------------------------
    # add package to shipment
    def addShippingPackage(self, packageWeight, physicalPackagingType, packagingType, packageWeightUnit="KG"):
        package_weight = self.shipment.create_wsdl_object_of_type("Weight")
        package_weight.Value = packageWeight
        package_weight.Units = packageWeightUnit

        package = self.shipment.create_wsdl_object_of_type("RequestedPackageLineItem")
        package.PhysicalPackaging = physicalPackagingType
        package.Weight = package_weight

        self.shipment.add_package(package)
        self.shipment.RequestedShipment.TotalWeight = package_weight
        self.shipment.RequestedShipment.PackagingType = packagingType

    # ----------------------------------------------------
    # add information on duties
    def setDutiesPaymentInfo(self):
        mParty = self.shipment.create_wsdl_object_of_type("Party")
        mParty.AccountNumber = self.CONFIG_OBJ.account_number
        mParty.Address = self.shipment.RequestedShipment.Recipient.Address

        mPayor = self.shipment.create_wsdl_object_of_type("Payor")
        mPayor.ResponsibleParty = mParty

        mPayment = self.shipment.create_wsdl_object_of_type("Payment")
        mPayment.PaymentType = "RECIPIENT"  # change if sender should pay duties
        mPayment.Payor = mPayor

        mCustomsValue = self.shipment.create_wsdl_object_of_type("Money")
        mCustomsValue.Amount = self.invoice_info["Value"]
        mCustomsValue.Currency = self.invoice_info["Currency"]

        ccd = self.shipment.create_wsdl_object_of_type("CustomsClearanceDetail")
        ccd.Commodities = self.mCommodities
        ccd.CustomsValue = mCustomsValue
        ccd.DutiesPayment = mPayment
        self.shipment.RequestedShipment.CustomsClearanceDetail = ccd

    # ----------------------------------------------------
    # Set ETD (electronic trade documents) settings
    def setSpecialServices(self, doc_ids):
        # construct objects
        ssr = self.shipment.create_wsdl_object_of_type("ShipmentSpecialServicesRequested")
        ssr.SpecialServiceTypes.append("ELECTRONIC_TRADE_DOCUMENTS")
        ssr.SpecialServiceTypes.append("EVENT_NOTIFICATION")

        # set up ETD details
        etd = self.shipment.create_wsdl_object_of_type("EtdDetail")
        etd.RequestedDocumentCopies = "COMMERCIAL INVOICE"

        for i, doc_id in enumerate(doc_ids, start=0):
            udrd = self.shipment.create_wsdl_object_of_type("UploadDocumentReferenceDetail")
            udrd.DocumentType = "COMMERCIAL_INVOICE" if i == 0 else "OTHER"
            udrd.DocumentId = doc_id
            udrd.Description = "Commercial_Invoice" if i == 0 else "Product_Description"
            udrd.DocumentIdProducer = "CUSTOMER"
            ssr.EtdDetail.DocumentReferences.append(udrd)

        self.shipment.RequestedShipment.SpecialServicesRequested = ssr

        # set Event Notification details
        send = self.shipment.create_wsdl_object_of_type("ShipmentEventNotificationDetail")
        send.AggregationType = "PER_SHIPMENT"

        sens = self.shipment.create_wsdl_object_of_type("ShipmentEventNotificationSpecification")
        sens.NotificationDetail.NotificationType = "EMAIL"
        sens.NotificationDetail.EmailDetail.EmailAddress = self.shipment.RequestedShipment.Recipient.Contact.EMailAddress
        sens.NotificationDetail.EmailDetail.Name = self.shipment.RequestedShipment.Recipient.Contact.PersonName
        sens.NotificationDetail.Localization.LanguageCode = "EN"
        sens.Role = "SHIPPER"
        sens.Events.append("ON_SHIPMENT")
        sens.Events.append("ON_EXCEPTION")
        sens.Events.append("ON_DELIVERY")
        sens.FormatSpecification.Type = "HTML"
        send.EventNotifications = sens
        self.shipment.RequestedShipment.SpecialServicesRequested.EventNotificationDetail = send

    # ----------------------------------------------------
    # process the shipment
    def processInternationalShipment(self):
        from shutil import copyfile

        self.shipment.RequestedShipment.ShipTimestamp = datetime.datetime.now().replace(microsecond=0).isoformat()

        # print(" ---- **** DETAILS ---- ****")
        # print(self.shipment.RequestedShipment)
        # print(self.shipment.ClientDetail)
        # print(self.shipment.TransactionDetail)
        # print("REQUESTED SHIPMENT\n\n", self.shipment.RequestedShipment)

        self.shipment.send_request()

        # print("RESPONSE\n\n", self.shipment.response)

        status = self.shipment.response.HighestSeverity

        if status == "SUCCESS" and "CompletedShipmentDetail" in self.shipment.response:
            shipment_details = self.shipment.response.CompletedShipmentDetail
            package_details = shipment_details.CompletedPackageDetails[0]
            tracking_id = package_details.TrackingIds[0].TrackingNumber
            email = self.shipment.RequestedShipment.Recipient.Contact.EMailAddress
            fedex_cost = "N/A"

            if hasattr(package_details, "PackageRating"):
                fedex_cost = package_details.PackageRating.PackageRateDetails[0].NetCharge.Amount

            # create the shipping PDF label
            ascii_label_data = package_details.Label.Parts[0].Image
            label_binary_data = binascii.a2b_base64(ascii_label_data)
            out_path = self.invoice_info["InvoiceId"] + f"_shipment_label_{tracking_id}.pdf"

            out_file = open(out_path, "wb")
            out_file.write(label_binary_data)
            out_file.close()

            # print output information
            print(
                f"- SUCCESS: Created FedEx label for invoice {self.invoice_info['InvoiceId']}\n     tracking ID: {tracking_id}\n     email: {email}\n     FedEx cost: {fedex_cost}\n     Customs value: {self.invoice_info['Value']} {self.invoice_info['Currency']}\n     Weight: {self.invoice_info['Weight']}\n     output path: {out_path}"
            )


# ----------------------------------------------------
# main script
commercial_invoice_path = "commercial_invoice_test.pdf"
product_description_1_path = "product_description_test.pdf"

sender = {
    "Company": "Sender Company",
    "Name": "Mr Smith",
    "Address": ["Address 1", "Address 2"],
    "Region": "",
    "Zip": "8230",
    "City": "Abyhoj",
    "Country": "Denmark",
    "Phone": "12345678",
    "Email": "<a href="https://stackoverflow.com/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="ee838f8782ae838f8782c08d8183" rel="noreferrer noopener nofollow">[email protected]</a>",
    "CountryCode": "DK",
    "Currency": "EUR",
    "VAT": "DK12345678",
    "Residential": False,
}

recipient = {
    "Company": "Recipient Co",
    "Name": "Contact Name",
    "Address": ["Adr1, Adr2"],
    "Region": "MN",
    "Zip": "55420",
    "City": "Bloomington",
    "Country": "United States",
    "Phone": "0123456789",
    "Email": "<a href="https://stackoverflow.com/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="8be6eae2e7cbe6eae2e7a5e8e4e6" rel="noreferrer noopener nofollow">[email protected]</a>",
    "CountryCode": "US",
    "Currency": "EUR",
    "VAT": "",
    "Residential": False,
}

invoice_info = {
    "InvoiceId": "14385",
    "Weight": 0.11,
    "Quantity": 2,
    "Value": 20.0,
    "Shipping": 25.0,
    "ShippingExpress": True,
    "Currency": "EUR",
    "InvoicePath": commercial_invoice_path,
    "Pdfs": [product_description_1_path],
}

# print output
print(f"\n- recipient: {recipient}\n- invoice_info: {invoice_info}\n")

# create FedEx Label Helper and set configuration
flh = FedexLabelHelper()
flh.setShipmentConfig(CONFIG_OBJ=CONFIG_OBJ, invoice_info=invoice_info)

# add sender & recipient info to FedEx shipment
flh.setSenderInfo(sender)
flh.setRecipientInfo(recipient)

# set packaging based on weight
flh.set_packaging_info()

# add reference to CI as only commodity info
flh.add_ci_commodity()

# set duties payment information
flh.setDutiesPaymentInfo()

# upload documents
doc_ids = flh.upload_all_documents()

# link uploaded documents as ETD and setup event notifications
flh.setSpecialServices(doc_ids)

# process shipments and create shipping labels
flh.processInternationalShipment()

关于python - 如何在 python-fedex 中为国际货件添加海关值(value)?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58949887/

相关文章:

xml - 为 FedEx Web 服务创建 HTTP Post 调用

magento-1.7 - Magento 1.7.0.2 FedEx 和 DHL 不工作

python - 有没有一种简单的方法可以随机化给定文本中的所有单词?也许在 BASH 中?

python - 在 Python 单元测试和主代码中访问资源文件

python - new.instancemethod 在重载脚本中转换为 python 3.3

python - SOAPpy 中的 namespace 未按预期工作

java - 是否可以覆盖 glassfish\modules\webservices-osgi.jar 中的类?

python - Django |反向 'user-posts' 参数 '(' ', )' not found. 1 pattern(s) tried: [' user/(?P<username>[^/]+)$']

c - Onvif - 试图了解它是如何工作的

php - 通过 WSDL/SOAP 使用 Fedex Webservice 的问题