Related
I have this problem with my code. When Iinsert three or more params in the body request, I get this Error "POST Error: or_ expected 2 arguments, got 3."
I can only pass one or two parameters in the body, in this case it works fine. But I don't understand where is the mistake. Can someone help me?
def read_uptime(logid, filteredData, dateStart, dateEnd, timeStart, timeEnd, elementsForPage, currentPage, filterUptime):
log.info(f"{logid} read_uptime: Started")
try:
# Check Timeframe Correct
startDateTime, endDateTime = _checkDataInput(timeStart, timeEnd, dateStart, dateEnd)
# Create Filter
filters = _createFilter(filteredData, startDateTime, endDateTime, filterUptime)
# Query
dataFiltered = uptime_model_db.query.with_entities(
uptime_model_db.projectId.label('projectId'),
uptime_model_db.url.label('url'),
uptime_model_db.timeStamp.label('timeStamp'),
uptime_model_db.uptime.label('uptime'),
uptime_model_db.latency.label('latency')
).filter(*filters).paginate(per_page=int(elementsForPage + 1), page=int(currentPage), error_out=True)
# Checking more pages
nextPage = {
"currentPage": currentPage,
"totalElements": len(dataFiltered.items)
}
if (len(dataFiltered.items) > elementsForPage):
nextPage["nextPage"] = True
else:
nextPage["nextPage"] = False
# Format and return JSON
return _createJson(dataFiltered.items, nextPage)
except Exception as e:
log.error(f"{logid} read_uptime: function read_uptime returned {e}")
raise e
i get in this code the mistake: "array.Filter.append(and_(uptime_model.db.porjectId == projectId, or_(*arrayUrl))"
def filterAppend(arrayFilter, urls, projectId, arrayUrl):
if(len(urls) == 1):
arrayFilter.append(and_(uptime_model_db.projectId == projectId, uptime_model_db.url == urls[0]))
if(len(urls) > 1):
for url in urls:
arrayUrl.append(uptime_model_db.url == url)
arrayFilter.append(and_(uptime_model_db.projectId == projectId, or_(*arrayUrl)))
i get in this code the mistake:
"filters.append(or_(*arrayFilter))"
def _createFilter(filteredData, startDateTime, endDateTime, filterUptime):
filters = []
if filteredData is not None:
arrayFilter = []
for data in filteredData:
projectId = data["projectId"]
urls = data["uptimeUrls"]
arrayUrl = []
if (len(filteredData) == 1):
filterAppend(filters, urls, projectId, arrayUrl)
else:
filterAppend(arrayFilter, urls, projectId, arrayUrl)
if(len(filteredData) > 1 or len(arrayFilter) > 1):
filters.append(or_(*arrayFilter))
if startDateTime is not None:
filters.append(str(startDateTime) <= uptime_model_db.timeStamp)
if startDateTime is not None:
filters.append(str(endDateTime) >= uptime_model_db.timeStamp)
if filterUptime == "True":
filters.append(uptime_model_db.uptime < 100)
return filters
import or_ from sqlalchemy instead of operators:
from sqlalchemy import or_
I'm using the python-fedex module as a light wrapper for the FedEx SOAP API. As part of this, I'm trying to set up a basic example of an international shipment, but I'm getting stuck with the following error message:
fedex.base_service.FedexError: Customs Value is required. (Error code: 2033)
I believe I need to add the products I ship as commodities, incl. their customs value - but I struggle to get this to work. I found this link with some guidance (from C#), but I was unable to get it to work in Python. Any inputs are appreciated!
My code is below:
# !/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()
Your need to add more information.
Insert the following codes before shipment.send_request(), then try again.
shipment.RequestedShipment.CustomsClearanceDetail.CustomsValue.Currency = 'USD'
shipment.RequestedShipment.CustomsClearanceDetail.CustomsValue.Amount = 1.0
shipment.RequestedShipment.CustomsClearanceDetail.DutiesPayment.PaymentType = 'SENDER'
shipment.RequestedShipment.CustomsClearanceDetail.DutiesPayment.Payor.ResponsibleParty.AccountNumber = CONFIG_OBJ.account_number
commodity1 = shipment.create_wsdl_object_of_type('Commodity')
commodity1.Name = 'book'
commodity1.NumberOfPieces = 1
commodity1.Description = '1'
commodity1.CountryOfManufacture = 'CN'
commodity1.HarmonizedCode = '123456789'
commodity1.Quantity = 1.0
commodity1.QuantityUnits = 'EA'
commodity1.Weight.Value = 1.0
commodity1.Weight.Units = "LB"
commodity1.CustomsValue.Currency = 'USD'
commodity1.CustomsValue.Amount = 1.0
commodity1.UnitPrice.Currency = 'USD'
commodity1.UnitPrice.Amount = 1.0
shipment.RequestedShipment.CustomsClearanceDetail.Commodities = [commodity1]
I have added a full international shipment example below, which solves this:
"""
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": "mail#mail.com",
"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": "mail#mail.com",
"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()
i have a problem, i have 2 float computed fields. their result and value could be seen if i logged in as an adminstrator, but couldnt be seen if i logged in as a normal user. even ive set the security in my modul here is the field :
class overtime_details(models.Model):
_name='overtime.overtime_details'
ovrtm = fields.Float(compute=attd_check, string='Overtime Hour(s)')
ttalmtp = fields.Float(compute=overtype_count, string='Total Multiplier')
and here is the picture when i logged in as a normal user :
then here is the picture when i logged in as administrator :
and here is my security permission csv :
id,name,model_id:id,group_id:id,perm_read,perm_write,perm_create,perm_unlink
overtime_formsec,overtime_formsec,model_overtime_overtime,,1,1,1,1
overtime_employee_list,overtime_employee_list,model_overtime_overtime_details,,1,1,1,1
overtime_type_list,overtime_type_list,model_overtime_type_overtime,,1,1,1,1
overtime_type_hours,overtime_type_hours,model_overtime_hour_overtime,,1,1,1,1
and here is the attd_check function :
#api.model
def attd_check(self):
#import pdb;pdb.set_trace()
for attds in self:
if attds.id:
ov = 0.0
attd = self.env['hr.attendance']
paratime = (datetime.strptime(attds.overtime_id.start_date, "%Y-%m-%d %H:%M:%S") - relativedelta(days=1, hours=7)).strftime("%Y-%m-%d 23:59:59")
signin = attd.search([('name','<=',attds.overtime_id.start_date),
('name','>',paratime),
('employee_id','=',attds.employee_id.id), ('action','=','sign_in')])
signout = attd.search([('name','>=',attds.overtime_id.end_date),
('employee_id','=',attds.employee_id.id), ('action','=','sign_out')])
signout2 = attd.search([('name','<',attds.overtime_id.end_date), ('name','>',attds.overtime_id.start_date),
('employee_id','=',attds.employee_id.id), ('action','=','sign_out')])
if signin:
if signout:
ov = attds.env['overtime.overtime'].calc_overtime(attds.overtime_id.start_date, attds.overtime_id.end_date)
elif signout2:
paramtole = datetime.strptime(signout2.name, "%Y-%m-%d %H:%M:%S").strftime("%M:%S")
tolerate = datetime.strptime("15:00", "%M:%S").strftime("%M:%S")
tolerate2 = datetime.strptime(str(attds.overtime_id.tolerance), "%M.%S").strftime("%M:%S")
if paramtole >= tolerate2 :
ov = attds.env['vit_overtime.overtime'].calc_overtime(attds.overtime_id.start_date, signout2.name) + 1
elif paramtole < tolerate :
ov = attds.env['overtime.overtime'].calc_overtime(attds.overtime_id.start_date, signout2.name)
else :
ov = attds.env['overtime.overtime'].calc_overtime(attds.overtime_id.start_date, signout2.name)
else:
ov = 0.0
else:
ov = 0.0
attds.ovrtm = ov
overtype count function :
#api.model
def overtype_count(self):
#import pdb;pdb.set_trace()
for det in self:
if det.id:
check = self.env['overtime.hour_overtime'].search([('hour_id.code','=',det.overtime_id.overtimetype_id.code)])
if check:
if det.overtime_id.state == 'done':
ovt=0
counter = 1
for hou in check:
if det.ovrtm <= 0:
det.ovrtm = ovt
elif counter <= det.ovrtm:
ttal = ovt + hou.calc
ovt = ttal
counter = counter + 1
else :
det.ttalmtp = ovt
else :
det.ttalmtp = 0
what should i do to resolve this, thanks before :)
i have solved this, so i added sudo() before search or browse in my function,
example:
before:
signin = attd.search([('name','<=',attds.overtime_id.start_date),
('name','>',paratime),
('employee_id','=',attds.employee_id.id), ('action','=','sign_in')])
after adding sudo():
signin = attd.sudo().search([('name','<=',attds.overtime_id.start_date),
('name','>',paratime),
('employee_id','=',attds.employee_id.id), ('action','=','sign_in')])
in view.py
Id = [2,3,4,5,6,7,8]
for w in Id:
A = w
Pending = pending(A)
data = {
'Pending': Pending,
}
return render_to_response('dialer_campaign/campaign/list.html', data, context_instance=RequestContext(request))
def pending(campaign_id):
A = Campaign_phonebook.objects.values_list('phonebook_id').filter(campaign_id = campaign_id)
B = Contact.objects.filter(phonebook_id__in=A).count()
C = Subscriber.objects.filter(campaign_id = campaign_id).exclude(status = 1).count()
Result = B - C
return Result
When i add manual value instead of A it gives result,but now i want to give value by for loop it is not working.Why ? Can anybody Help me ?
Want changes should i do in templates ?
Thanks in Advance..
Take your data object in list and render to the template
Refer following code
Id = [2,3,4,5,6,7,8]
pending_list = []
for w in Id:
pending = pending(w)
pending_list.append({'pending': pending})
return render_to_response('dialer_campaign/campaign/list.html', pending_list, context_instance=RequestContext(request))
def pending(campaign_id):
A = Campaign_phonebook.objects.values_list('phonebook_id').filter(campaign_id = campaign_id)
B = Contact.objects.filter(phonebook_id__in=A).count()
C = Subscriber.objects.filter(campaign_id = campaign_id).exclude(status = 1).count()
Result = B - C
return Result
Use pending_list in your template. In pending_list list you get all the pending objects.
I am porting some Java code to Python and we would like to use Python 3 but I can't find LDAP module for Python 3 in Windows.
This is forcing us to use 2.6 version and it is bothersome as rest of the code is already in 3.0 format.
You may use ldap3 module (formerly known as python3-ldap), it runs on python3 really well and requires no external C dependances. Also it can correctly handle both unicode and byte data in ldap records (in early versions there was a trouble with jpegPhoto field, now everything is fine)
If you're running this on Windows, you can get LDAP to work in Python 3.1 by using the ADO access method via Mark Hammond's PyWin32.
To test this, I installed ActiveState Python 3.1, then installed PyWin32 for Python 3.1
http://sourceforge.net/projects/pywin32/files/
I was then able to run LDAP queries using a module I wrote that is based on this LDAP code from the ActiveState Python Cookbook:
Recipe 511451: Dump all Active Directory Information using LDAP scripting by Manuel Garcia
http://code.activestate.com/recipes/511451/
although now that I look at it I realize I completely rewrote my module just using his code as an example.
Update
Here is my LDAPList module and another support module to convert user access bit codes into something a tiny bit more english-like:
LDAPList.py
# LDAPList.py
# Todd Fiske
# class to encapsulate accessing LDAP information
# 2009-03-18 first version
# 2010-01-04 updated for Python 3 (print functions, <> to !=)
import win32com.client
import UACCodes
ADS_SCOPE_SUBTREE = 2
class LDAPList():
def __init__(self, sContext):
self.Context = sContext # naming context, "DC=xyz,DC=org"
self.objectCategory = ""
self.objectClass = ""
self.FilterClause = ""
self.query = ""
self.cn = None
self.cm = None
self.rs = None
def SetCategory(self, sCategory):
self.objectCategory = sCategory
self.FilterClause = "where objectCategory = '%s'" % self.objectCategory
def SetClass(self, sClass):
self.objectClass = sClass
self.FilterClause = "where objectClass = '%s'" % self.objectClass
def open(self):
self.query = "select * from 'LDAP://%s' %s order by displayName" % (self.Context, self.FilterClause)
self.cn = win32com.client.Dispatch("ADODB.Connection")
self.cm = win32com.client.Dispatch("ADODB.Command")
self.cn.Open("Provider=ADsDSOObject")
self.cm.ActiveConnection = self.cn
self.cm.Properties["Page Size"] = 1000
self.cm.Properties["Searchscope"] = ADS_SCOPE_SUBTREE
self.cm.CommandText = self.query
self.rs = self.cm.Execute()[0]
def close(self):
if self.rs is not None:
self.rs.Close()
self.rs = None
if self.cm is not None:
self.cm = None
if self.cn is not None:
self.cn.Close()
self.cn = None
def count(self):
if self.rs is None:
return -2
return self.rs.RecordCount
def more(self):
if self.rs is None:
return False
return not self.rs.EOF
def GetObject(self):
if self.rs is None:
return None
return win32com.client.GetObject(self.rs.Fields["ADsPath"].Value)
def next(self):
if self.rs is None:
return
self.rs.MoveNext()
#----------
# helper functions
def NamingContext():
# return default naming context
root = win32com.client.GetObject("LDAP://RootDse")
return root.get("DefaultNamingContext")
def AccountControl(obj):
if obj.userAccountControl is not None:
return obj.userAccountControl
else:
return 0
def ConvertUAC(nUAC):
return UACCodes.ConvertUAC(nUAC)
def AccountActive(n):
return (n & UACCodes.ADS_UF_ACCOUNTDISABLE) != UACCodes.ADS_UF_ACCOUNTDISABLE
def GetCategory(obj):
# CN=Group,CN=Schema,CN=Configuration,DC=xyz,DC=org
s = obj.objectCategory
s = s.split(",")[0][3:]
return s
# s = "Group"
def GetGroups(obj):
"""
('CN=XYZ Staff Rockville,OU=Distribution Groups,DC=xyz,DC=org',
'CN=XYZ Staff,OU=Distribution Groups,DC=xyz,DC=org')
"""
if obj.memberOf is None:
return ""
if type(obj.memberOf)==type(()):
tGroups = obj.memberOf
else:
tGroups = (obj.memberOf,)
return tGroups
def GetNameParts(obj):
if obj.givenName is None:
sFirst = ""
else:
sFirst = obj.givenName
if obj.middleName is None:
sMiddle = ""
else:
sMiddle = obj.middleName
if obj.sn is None:
sLast = ""
else:
sLast = obj.sn
if sLast == "" and sFirst == "":
if obj.name is not None:
sName = obj.name
sName = sName[3:]
lParts = sName.split(" ")
if len(lParts) == 1:
"todo: split on embedded capital letter"
print("single-part name: %s" % sName)
sFirst = sName
else:
sLast = lParts[-1]
sFirst = " ".join(lParts[:-1])
return (sFirst, sMiddle, sLast)
def GetManager(obj):
if obj.manager is None:
return ""
else:
return obj.manager
#----------
# test
if __name__ == "__main__":
print
print("testing LDAPList class")
nc = NamingContext()
print("context =", nc)
ll = LDAPList(nc)
ll.SetCategory('user')
ll.open() # generates recordset
print("query = %s" % ll.query)
print("%d items" % ll.count())
n = 0
while (n < 10) and (ll.more()):
o = ll.GetObject() # return
nUAC = AccountControl(o)
print("%-30s %-30s %-30s %-40s %s" % (
o.displayName,
o.name,
o.sAMAccountName,
UACCodes.ConvertUAC(nUAC),
GetManager(o)
))
n += 1
ll.next()
ll.close()
###
UACCodes.py
# UACCodes.py
# Todd Fiske
# generated 2009-09-23 16:36:56 by BuildUACCodes.py
# updated 2010-01-04 for Python 3 (print functions)
# provide UAC constants, lookup list, and conversion function
import sys
# UAC Constants
ADS_UF_SCRIPT = 0x00000001
ADS_UF_ACCOUNTDISABLE = 0x00000002
ADS_UF_HOMEDIR_REQUIRED = 0x00000008
ADS_UF_LOCKOUT = 0x00000010
ADS_UF_PASSWD_NOTREQD = 0x00000020
ADS_UF_PASSWD_CANT_CHANGE = 0x00000040
ADS_UF_ENCRYPTED_TEXT_PASSWORD_ALLOWED = 0x00000080
ADS_UF_TEMP_DUPLICATE_ACCOUNT = 0x00000100
ADS_UF_NORMAL_ACCOUNT = 0x00000200
ADS_UF_INTERDOMAIN_TRUST_ACCOUNT = 0x00000800
ADS_UF_WORKSTATION_TRUST_ACCOUNT = 0x00001000
ADS_UF_SERVER_TRUST_ACCOUNT = 0x00002000
ADS_UF_DONT_EXPIRE_PASSWD = 0x00010000
ADS_UF_MNS_LOGON_ACCOUNT = 0x00020000
ADS_UF_SMARTCARD_REQUIRED = 0x00040000
ADS_UF_TRUSTED_FOR_DELEGATION = 0x00080000
ADS_UF_NOT_DELEGATED = 0x00100000
ADS_UF_USE_DES_KEY_ONLY = 0x00200000
ADS_UF_DONT_REQUIRE_PREAUTH = 0x00400000
ADS_UF_PASSWORD_EXPIRED = 0x00800000
ADS_UF_TRUSTED_TO_AUTHENTICATE_FOR_DELEGATION = 0x01000000
# UAC short name lookup list
lUACCodes = [
("ADS_UF_SCRIPT" , 0x00000001, "script"),
("ADS_UF_ACCOUNTDISABLE" , 0x00000002, "disabled"),
("ADS_UF_HOMEDIR_REQUIRED" , 0x00000008, "homedir"),
("ADS_UF_LOCKOUT" , 0x00000010, "lockout"),
("ADS_UF_PASSWD_NOTREQD" , 0x00000020, "pwnotreqd"),
("ADS_UF_PASSWD_CANT_CHANGE" , 0x00000040, "pwcantchange"),
("ADS_UF_ENCRYPTED_TEXT_PASSWORD_ALLOWED" , 0x00000080, "encryptedpw"),
("ADS_UF_TEMP_DUPLICATE_ACCOUNT" , 0x00000100, "dupaccount"),
("ADS_UF_NORMAL_ACCOUNT" , 0x00000200, "useracct"),
("ADS_UF_INTERDOMAIN_TRUST_ACCOUNT" , 0x00000800, "interdomain"),
("ADS_UF_WORKSTATION_TRUST_ACCOUNT" , 0x00001000, "workstation"),
("ADS_UF_SERVER_TRUST_ACCOUNT" , 0x00002000, "server"),
("ADS_UF_DONT_EXPIRE_PASSWD" , 0x00010000, "pwnoexpire"),
("ADS_UF_MNS_LOGON_ACCOUNT" , 0x00020000, "mnslogon"),
("ADS_UF_SMARTCARD_REQUIRED" , 0x00040000, "smartcard"),
("ADS_UF_TRUSTED_FOR_DELEGATION" , 0x00080000, "trustdeleg"),
("ADS_UF_NOT_DELEGATED" , 0x00100000, "notdeleg"),
("ADS_UF_USE_DES_KEY_ONLY" , 0x00200000, "deskey"),
("ADS_UF_DONT_REQUIRE_PREAUTH" , 0x00400000, "nopreauth"),
("ADS_UF_PASSWORD_EXPIRED" , 0x00800000, "pwexpired"),
("ADS_UF_TRUSTED_TO_AUTHENTICATE_FOR_DELEGATION", 0x01000000, "trustauth"),
]
# UAC conversion function
def ConvertUAC(nUAC):
s = ""
for c in lUACCodes:
if ((nUAC & c[1]) == c[1]):
s = s + c[2] + " "
return s
# test routine
if __name__ == "__main__":
print("UACCodes Test")
print("-------------")
for n in [0, 512, 514, 65535]:
print("%d = %s" % (n, ConvertUAC(n)))
print
for s in sys.argv[1:]:
n = int(s)
print("%d = %s" % (n, ConvertUAC(n)))
###
Both modules have some usage examples and should be fairly easy to figure out, but let me know if you have any questions or comments.
There is a Pure Python implementation of an LDAP client called Ldaptor. I don't think it's maintained though. If you really need it, you might be able to run 2to3 on this and port it.
This answer is no longer accurate; see below for other answers.
Sorry to break this on you, but I don't think there is a python-ldap for Python 3 (yet)...
That's the reason why we should keep active development at Python 2.6 for now (as long as most crucial dependencies (libs) are not ported to 3.0).