read_listdata() --> classmethod
This commit is contained in:
parent
cf98fdf2ad
commit
530f37a06b
1 changed files with 72 additions and 59 deletions
131
document.py
131
document.py
|
@ -7,6 +7,7 @@
|
||||||
|
|
||||||
import os.path
|
import os.path
|
||||||
import json
|
import json
|
||||||
|
import copy
|
||||||
from lxml import etree
|
from lxml import etree
|
||||||
from datetime import datetime, date
|
from datetime import datetime, date
|
||||||
from decimal import Decimal
|
from decimal import Decimal
|
||||||
|
@ -633,6 +634,8 @@ class Incoming(metaclass=PoolMeta):
|
||||||
line.account = expense_accounts[0]
|
line.account = expense_accounts[0]
|
||||||
|
|
||||||
# check if calculated 'amount' matches with amount from xml-data
|
# check if calculated 'amount' matches with amount from xml-data
|
||||||
|
assert invoice.currency is not None
|
||||||
|
|
||||||
xml_amount = line_data.get('total', {}).pop('amount', None)
|
xml_amount = line_data.get('total', {}).pop('amount', None)
|
||||||
if xml_amount is not None:
|
if xml_amount is not None:
|
||||||
if xml_amount != line.get_amount(None):
|
if xml_amount != line.get_amount(None):
|
||||||
|
@ -667,10 +670,43 @@ class Incoming(metaclass=PoolMeta):
|
||||||
'document_incoming_invoice_xml.msg_unused_linevalues'),
|
'document_incoming_invoice_xml.msg_unused_linevalues'),
|
||||||
json.dumps(line_data, cls=JSONEncoder, indent=3)])
|
json.dumps(line_data, cls=JSONEncoder, indent=3)])
|
||||||
line.note = '\n'.join(x for x in notes if x)
|
line.note = '\n'.join(x for x in notes if x)
|
||||||
|
|
||||||
line.on_change_invoice()
|
line.on_change_invoice()
|
||||||
return line
|
return line
|
||||||
|
|
||||||
|
def _readxml_read_listdata(self, xmldata, xpth, xtag, key_list):
|
||||||
|
""" read list of values from xml
|
||||||
|
|
||||||
|
Args:
|
||||||
|
xmldata (xtree): xml-tree
|
||||||
|
xpth (list): list of xml-tags until index-counter
|
||||||
|
pos (int): position in list
|
||||||
|
xtag (str): xml-tag to read as list
|
||||||
|
key_list (list): [('<xtag>', '<key>')]
|
||||||
|
|
||||||
|
Returns:
|
||||||
|
list: list of dict
|
||||||
|
"""
|
||||||
|
if isinstance(xtag, str):
|
||||||
|
xtag = [xtag]
|
||||||
|
xpath_list = xpth + xtag
|
||||||
|
num_listitem = len(xmldata.xpath(
|
||||||
|
self._readxml_xpath(xpath_list), namespaces=xmldata.nsmap))
|
||||||
|
listdata = []
|
||||||
|
for x in range(1, num_listitem + 1):
|
||||||
|
values = {}
|
||||||
|
for list_item in key_list:
|
||||||
|
(xkey, key, xtype) = (
|
||||||
|
list_item if len(list_item) == 3
|
||||||
|
else tuple(list(list_item) + [None]))
|
||||||
|
|
||||||
|
value = self._readxml_getvalue(
|
||||||
|
xmldata, xpath_list + [x, xkey], vtype=xtype)
|
||||||
|
if value is not None:
|
||||||
|
values[key] = value
|
||||||
|
if values:
|
||||||
|
listdata.append(values)
|
||||||
|
return listdata
|
||||||
|
|
||||||
def _readxml_invoice_line(self, xmldata, xpth, pos):
|
def _readxml_invoice_line(self, xmldata, xpth, pos):
|
||||||
""" read invoice-line from xml
|
""" read invoice-line from xml
|
||||||
|
|
||||||
|
@ -682,43 +718,13 @@ class Incoming(metaclass=PoolMeta):
|
||||||
Returns:
|
Returns:
|
||||||
dict: invoice line data
|
dict: invoice line data
|
||||||
"""
|
"""
|
||||||
def read_listdata(xtag, key_list):
|
xpath_line = xpth + [pos]
|
||||||
""" read list of values from xml
|
|
||||||
|
|
||||||
Args:
|
|
||||||
xtag (str): xml-tag to read as list
|
|
||||||
key_list (list): [('<xtag>', '<key>')]
|
|
||||||
|
|
||||||
Returns:
|
|
||||||
list: list of dict
|
|
||||||
"""
|
|
||||||
if isinstance(xtag, str):
|
|
||||||
xtag = [xtag]
|
|
||||||
xpath_list = xpth + [pos] + xtag
|
|
||||||
num_listitem = len(xmldata.xpath(
|
|
||||||
self._readxml_xpath(xpath_list), namespaces=xmldata.nsmap))
|
|
||||||
listdata = []
|
|
||||||
for x in range(1, num_listitem + 1):
|
|
||||||
values = {}
|
|
||||||
for list_item in key_list:
|
|
||||||
(xkey, key, xtype) = (
|
|
||||||
list_item if len(list_item) == 3
|
|
||||||
else tuple(list(list_item) + [None]))
|
|
||||||
|
|
||||||
value = self._readxml_getvalue(
|
|
||||||
xmldata, xpath_list + [x, xkey], vtype=xtype)
|
|
||||||
if value is not None:
|
|
||||||
values[key] = value
|
|
||||||
if values:
|
|
||||||
listdata.append(values)
|
|
||||||
return listdata
|
|
||||||
|
|
||||||
result = {'convert_note': []}
|
result = {'convert_note': []}
|
||||||
result['line_no'] = self._readxml_getvalue(xmldata, xpth + [pos] + [
|
result['line_no'] = self._readxml_getvalue(xmldata, xpath_line + [
|
||||||
'ram:AssociatedDocumentLineDocument', 'ram:LineID'])
|
'ram:AssociatedDocumentLineDocument', 'ram:LineID'])
|
||||||
|
|
||||||
result['line_note'] = '\n'.join(self._readxml_getvalue(
|
result['line_note'] = '\n'.join(self._readxml_getvalue(
|
||||||
xmldata, xpth + [pos] + [
|
xmldata, xpath_line + [
|
||||||
'ram:AssociatedDocumentLineDocument', 'ram:IncludedNote',
|
'ram:AssociatedDocumentLineDocument', 'ram:IncludedNote',
|
||||||
'ram:Content'], allow_list=True))
|
'ram:Content'], allow_list=True))
|
||||||
|
|
||||||
|
@ -736,34 +742,38 @@ class Incoming(metaclass=PoolMeta):
|
||||||
('ram:ModelName', 'model_name'),
|
('ram:ModelName', 'model_name'),
|
||||||
('ram:OriginTradeCountry', 'trade_country')
|
('ram:OriginTradeCountry', 'trade_country')
|
||||||
]:
|
]:
|
||||||
result[key] = self._readxml_getvalue(xmldata, xpth + [pos] + [
|
result[key] = self._readxml_getvalue(xmldata, xpath_line + [
|
||||||
'ram:SpecifiedTradeProduct', xkey])
|
'ram:SpecifiedTradeProduct', xkey])
|
||||||
|
|
||||||
# attributes of product
|
# attributes of product
|
||||||
result['attributes'] = read_listdata([
|
result['attributes'] = self._readxml_read_listdata(
|
||||||
'ram:SpecifiedTradeProduct',
|
xmldata, xpath_line, [
|
||||||
'ram:ApplicableProductCharacteristic'], [
|
'ram:SpecifiedTradeProduct',
|
||||||
|
'ram:ApplicableProductCharacteristic'], [
|
||||||
('ram:TypeCode', 'code'),
|
('ram:TypeCode', 'code'),
|
||||||
('ram:Description', 'description'),
|
('ram:Description', 'description'),
|
||||||
('ram:ValueMeasure', 'uom'),
|
('ram:ValueMeasure', 'uom'),
|
||||||
('ram:ValueY', 'value')])
|
('ram:ValueY', 'value')])
|
||||||
|
|
||||||
# classification of product
|
# classification of product
|
||||||
result['classification'] = read_listdata([
|
result['classification'] = self._readxml_read_listdata(
|
||||||
'ram:SpecifiedTradeProduct',
|
xmldata, xpath_line, [
|
||||||
'ram:DesignatedProductClassification'], [
|
'ram:SpecifiedTradeProduct',
|
||||||
|
'ram:DesignatedProductClassification'], [
|
||||||
('ram:ClassCode', 'code'),
|
('ram:ClassCode', 'code'),
|
||||||
('ram:ClassName', 'name')])
|
('ram:ClassName', 'name')])
|
||||||
|
|
||||||
# serial-numbers of product
|
# serial-numbers of product
|
||||||
result['serialno'] = read_listdata([
|
result['serialno'] = self._readxml_read_listdata(
|
||||||
'ram:SpecifiedTradeProduct',
|
xmldata, xpath_line, [
|
||||||
'ram:IndividualTradeProductInstance'], [
|
'ram:SpecifiedTradeProduct',
|
||||||
|
'ram:IndividualTradeProductInstance'], [
|
||||||
('ram:BatchID', 'lot'),
|
('ram:BatchID', 'lot'),
|
||||||
('ram:SupplierAssignedSerialID', 'serial')])
|
('ram:SupplierAssignedSerialID', 'serial')])
|
||||||
|
|
||||||
# referenced product
|
# referenced product
|
||||||
result['refprod'] = read_listdata(
|
result['refprod'] = self._readxml_read_listdata(
|
||||||
|
xmldata, xpath_line,
|
||||||
['ram:SpecifiedTradeProduct', 'ram:IncludedReferencedProduct'], [
|
['ram:SpecifiedTradeProduct', 'ram:IncludedReferencedProduct'], [
|
||||||
('ram:ID', 'id'),
|
('ram:ID', 'id'),
|
||||||
('ram:GlobalID', 'global_id'),
|
('ram:GlobalID', 'global_id'),
|
||||||
|
@ -775,12 +785,13 @@ class Incoming(metaclass=PoolMeta):
|
||||||
])
|
])
|
||||||
|
|
||||||
# net price
|
# net price
|
||||||
xpath_netprice = xpth + [pos] + [
|
xpath_netprice = xpath_line + [
|
||||||
'ram:SpecifiedLineTradeAgreement', 'ram:NetPriceProductTradePrice']
|
'ram:SpecifiedLineTradeAgreement', 'ram:NetPriceProductTradePrice']
|
||||||
if self._readxml_getvalue(xmldata, xpath_netprice):
|
if self._readxml_getvalue(xmldata, xpath_netprice):
|
||||||
result['unit_net_price'] = read_listdata([
|
result['unit_net_price'] = self._readxml_read_listdata(
|
||||||
'ram:SpecifiedLineTradeAgreement',
|
xmldata, xpath_line, [
|
||||||
'ram:NetPriceProductTradePrice'], [
|
'ram:SpecifiedLineTradeAgreement',
|
||||||
|
'ram:NetPriceProductTradePrice'], [
|
||||||
('ram:ChargeAmount', 'amount', Decimal),
|
('ram:ChargeAmount', 'amount', Decimal),
|
||||||
('ram:BasisQuantity', 'basequantity', Decimal)])[0]
|
('ram:BasisQuantity', 'basequantity', Decimal)])[0]
|
||||||
# notice ignored field
|
# notice ignored field
|
||||||
|
@ -791,13 +802,14 @@ class Incoming(metaclass=PoolMeta):
|
||||||
xpath_netprice + ['ram:AppliedTradeAllowanceCharge']))
|
xpath_netprice + ['ram:AppliedTradeAllowanceCharge']))
|
||||||
|
|
||||||
# gross price
|
# gross price
|
||||||
xpath_grossprice = xpth + [pos] + [
|
xpath_grossprice = xpath_line + [
|
||||||
'ram:SpecifiedLineTradeAgreement',
|
'ram:SpecifiedLineTradeAgreement',
|
||||||
'ram:GrossPriceProductTradePrice']
|
'ram:GrossPriceProductTradePrice']
|
||||||
if self._readxml_getvalue(xmldata, xpath_grossprice):
|
if self._readxml_getvalue(xmldata, xpath_grossprice):
|
||||||
result['unit_gross_price'] = read_listdata([
|
result['unit_gross_price'] = self._readxml_read_listdata(
|
||||||
'ram:SpecifiedLineTradeAgreement',
|
xmldata, xpath_line, [
|
||||||
'ram:GrossPriceProductTradePrice'], [
|
'ram:SpecifiedLineTradeAgreement',
|
||||||
|
'ram:GrossPriceProductTradePrice'], [
|
||||||
('ram:ChargeAmount', 'amount', Decimal),
|
('ram:ChargeAmount', 'amount', Decimal),
|
||||||
('ram:BasisQuantity', 'basequantity', Decimal)])[0]
|
('ram:BasisQuantity', 'basequantity', Decimal)])[0]
|
||||||
# notice ignored field
|
# notice ignored field
|
||||||
|
@ -809,9 +821,10 @@ class Incoming(metaclass=PoolMeta):
|
||||||
['ram:AppliedTradeAllowanceCharge']))
|
['ram:AppliedTradeAllowanceCharge']))
|
||||||
|
|
||||||
# quantity
|
# quantity
|
||||||
xpath_quantity = xpth + [pos] + ['ram:SpecifiedLineTradeDelivery']
|
xpath_quantity = xpath_line + ['ram:SpecifiedLineTradeDelivery']
|
||||||
result['quantity'] = read_listdata(
|
result['quantity'] = self._readxml_read_listdata(
|
||||||
['ram:SpecifiedLineTradeDelivery'], [
|
xmldata, xpath_line, [
|
||||||
|
'ram:SpecifiedLineTradeDelivery'], [
|
||||||
('ram:BilledQuantity', 'billed', Decimal),
|
('ram:BilledQuantity', 'billed', Decimal),
|
||||||
('ram:ChargeFreeQuantity', 'chargefree', Decimal),
|
('ram:ChargeFreeQuantity', 'chargefree', Decimal),
|
||||||
('ram:PackageQuantity', 'package', Decimal),
|
('ram:PackageQuantity', 'package', Decimal),
|
||||||
|
@ -829,8 +842,8 @@ class Incoming(metaclass=PoolMeta):
|
||||||
'skip: ' + self._readxml_xpath(xp_to_check))
|
'skip: ' + self._readxml_xpath(xp_to_check))
|
||||||
|
|
||||||
# taxes
|
# taxes
|
||||||
xpath_trade = xpth + [pos] + ['ram:SpecifiedLineTradeSettlement']
|
xpath_trade = xpath_line + ['ram:SpecifiedLineTradeSettlement']
|
||||||
result['taxes'] = read_listdata([
|
result['taxes'] = self._readxml_read_listdata(xmldata, xpath_line, [
|
||||||
'ram:SpecifiedLineTradeSettlement',
|
'ram:SpecifiedLineTradeSettlement',
|
||||||
'ram:ApplicableTradeTax'], [
|
'ram:ApplicableTradeTax'], [
|
||||||
('ram:CalculatedAmount', 'amount', Decimal),
|
('ram:CalculatedAmount', 'amount', Decimal),
|
||||||
|
@ -846,7 +859,7 @@ class Incoming(metaclass=PoolMeta):
|
||||||
('ram:RateApplicablePercent', 'percent', Decimal)])
|
('ram:RateApplicablePercent', 'percent', Decimal)])
|
||||||
|
|
||||||
# total amounts
|
# total amounts
|
||||||
result['total'] = read_listdata([
|
result['total'] = self._readxml_read_listdata(xmldata, xpath_line, [
|
||||||
'ram:SpecifiedLineTradeSettlement',
|
'ram:SpecifiedLineTradeSettlement',
|
||||||
'ram:SpecifiedTradeSettlementLineMonetarySummation'], [
|
'ram:SpecifiedTradeSettlementLineMonetarySummation'], [
|
||||||
('ram:LineTotalAmount', 'amount', Decimal),
|
('ram:LineTotalAmount', 'amount', Decimal),
|
||||||
|
|
Loading…
Reference in a new issue