|
@@ -56,6 +56,20 @@ const importXML = (() => {
|
|
|
// 费率、指数、比例(%)类小数精度
|
|
|
RATE: 3,
|
|
|
};
|
|
|
+ // 根据上方精度要求得到的项目属性,小数位数的值
|
|
|
+ const tenderPropertyDecimal = {
|
|
|
+ bills: { unitPrice: Decimal.FEE, totalPrice: Decimal.FEE },
|
|
|
+ ration: { quantity: Decimal.QUANTITY, unitPrice: Decimal.FEE, totalPrice: Decimal.FEE },
|
|
|
+ glj: { quantity: Decimal.GLJ, unitPriceHasMix: Decimal.FEE, unitPrice: Decimal.FEE },
|
|
|
+ feeRate: Decimal.RATE,
|
|
|
+ quantity_detail: 4,
|
|
|
+ material: 5,//三材系数
|
|
|
+ process: 6
|
|
|
+ };
|
|
|
+ const tenderPropertyBillsQuantityDecimal = Decimal.QUANTITY;
|
|
|
+ // 工程量表达式相关
|
|
|
+ const GCLMXHj = 'GCLMXHJ';
|
|
|
+ const QDL = 'QDL';
|
|
|
|
|
|
/*
|
|
|
* 从导入的xml文件中提取有用的数据
|
|
@@ -74,7 +88,7 @@ const importXML = (() => {
|
|
|
name: getValue(projectSrc, ['_Name']),
|
|
|
engs: extractEngs(projectSrc, xmlObjMap),
|
|
|
property: {
|
|
|
- compilationIllustrationProject: getValue(projectSrc, ['_Explains'])
|
|
|
+ compilationIllustration: getValue(projectSrc, ['_Explains'])
|
|
|
},
|
|
|
basicInformation: extractBasicInfo(projectSrc)
|
|
|
};
|
|
@@ -181,6 +195,7 @@ const importXML = (() => {
|
|
|
projType: projectType.Tender,
|
|
|
name: getValue(src, ['_Name']),
|
|
|
code: getValue(src, ['_Number']),
|
|
|
+ compilationIllustration: getValue(src, ['_Explains']),
|
|
|
engineering: getValue(src, ['_ProjectType']),
|
|
|
projectFeature: extractProjectFeature(src),
|
|
|
workSummary: extractWorkSummary(src),
|
|
@@ -293,15 +308,19 @@ const importXML = (() => {
|
|
|
jobContent: getJobContent(workElementSrc),
|
|
|
unit: getValue(workElementSrc, ['_Unit']),
|
|
|
quantity: getValue(workElementSrc, ['_Quantity']),
|
|
|
- feeRate: getValue(workElementSrc, ['_Rate']),
|
|
|
mainBills: getBool(getValue(workElementSrc, ['_Major'])),
|
|
|
feeCode: getValue(workElementSrc, ['_Code']),
|
|
|
remark: getValue(workElementSrc, ['_Remark']),
|
|
|
+ quantityDetails: extractQuantityDetails(workElementSrc),
|
|
|
rations: extractRations(workElementSrc)
|
|
|
};
|
|
|
if (type === billType.BILL) {
|
|
|
- // 分项不需要基数
|
|
|
+ // 分项不需要基数、费率
|
|
|
bills.calcBase = getValue(workElementSrc, ['_QtyFormula']);
|
|
|
+ const feeRate = getValue(workElementSrc, ['_Rate']);
|
|
|
+ if (+feeRate) {
|
|
|
+ bills.feeRate = feeRate;
|
|
|
+ }
|
|
|
}
|
|
|
// 投标和控制价,需要导入最高限价
|
|
|
if ([FileKind.tender, FileKind.control].includes(importFileKind)) {
|
|
@@ -369,6 +388,15 @@ const importXML = (() => {
|
|
|
}));
|
|
|
}
|
|
|
}
|
|
|
+ // 提取工程量明细(清单、定额底下都可能会有)
|
|
|
+ function extractQuantityDetails(src) {
|
|
|
+ return arrayValue(src, ['ExpressElement']).map(itemSrc => ({
|
|
|
+ seq: getValue(itemSrc, ['_OrderNumber']),
|
|
|
+ regex: getValue(itemSrc, ['_Express']),
|
|
|
+ result: getValue(itemSrc, ['_Quantity']),
|
|
|
+ isSummation: +getValue(itemSrc, ['_Kind'])
|
|
|
+ }));
|
|
|
+ }
|
|
|
// 提取定额
|
|
|
function extractRations(workElementSrc) {
|
|
|
if (importFileKind !== FileKind.tender) {
|
|
@@ -458,6 +486,7 @@ const importXML = (() => {
|
|
|
const feesFromCalcItem = getFeesFromCalculationOfItem(rationSrc);
|
|
|
ration.fees = mergeFees(fees, feesFromCalcItem);
|
|
|
ration.rationGLJs = extractRationGLJs(rationSrc);
|
|
|
+ ration.quantityDetails = extractQuantityDetails(rationSrc);
|
|
|
return ration;
|
|
|
}
|
|
|
}
|
|
@@ -834,7 +863,10 @@ const importXML = (() => {
|
|
|
gljLibIDs: tenderData.gljLibIDs,
|
|
|
shareInfo: []
|
|
|
};
|
|
|
- transformedTender.property.gljAdjustType = getAdjustType(tenderData)
|
|
|
+ transformedTender.property.compilationIllustration = tenderData.compilationIllustration;
|
|
|
+ transformedTender.property.gljAdjustType = getAdjustType(tenderData);
|
|
|
+ transformedTender.property.decimal = tenderPropertyDecimal;
|
|
|
+ transformedTender.property.billsQuantityDecimalValue = tenderPropertyBillsQuantityDecimal;
|
|
|
detailData.tender = transformedTender;
|
|
|
return detailData;
|
|
|
}
|
|
@@ -862,7 +894,6 @@ const importXML = (() => {
|
|
|
}
|
|
|
// 合并清单,将提取出来的清单相关数据,合并进项目清单(模板)
|
|
|
function mergeBills(tenderData, billsTemplate) {
|
|
|
- debugger;
|
|
|
const mergedBills = [...billsTemplate];
|
|
|
const roots = billsTemplate.filter(bills => bills.ParentID === -1);
|
|
|
let lastRoot = roots.find(root => root.NextSiblingID === -1);
|
|
@@ -924,6 +955,7 @@ const importXML = (() => {
|
|
|
// 合并大项费用
|
|
|
function mergeWorkSummary(workSummary) {
|
|
|
// 首层数据与清单模板根据费用字典进行匹配,匹配到的则赋值一些属性,匹配不到则将其及其所有子数据插入到模板最末大项费用
|
|
|
+ debugger;
|
|
|
workSummary.forEach(summaryBills => {
|
|
|
const matched = roots.find(root => FlagFeeCodeMap[getFlag(root)] === summaryBills.feeCode);
|
|
|
if (matched) {
|
|
@@ -948,13 +980,13 @@ const importXML = (() => {
|
|
|
// 合并措施项目
|
|
|
function mergeCSXM(csxmSrc) {
|
|
|
const fixedBills = billsTemplate.find(bills => getFlag(bills) === fixedFlag.MEASURE);
|
|
|
- fixedBills.fees = csxmSrc.fees;
|
|
|
+ fixedBills.fees = mergeFees(fixedBills.fees, csxmSrc.fees);
|
|
|
mergeitems(fixedBills, csxmSrc.items);
|
|
|
}
|
|
|
// 合并其他项目
|
|
|
function mergeOther(otherSrc) {
|
|
|
const fixedBills = billsTemplate.find(bills => getFlag(bills) === fixedFlag.OTHER);
|
|
|
- fixedBills.fees = otherSrc.fees;
|
|
|
+ fixedBills.fees = mergeFees(fixedBills.fees, otherSrc.fees);
|
|
|
// 合并其他项目费
|
|
|
|
|
|
// SundryCosts其他项目费会包含暂列金额等后续会再次出现的数据,因此合并SundryCosts的数据时,过滤掉一部分数据
|
|
@@ -1091,7 +1123,7 @@ const importXML = (() => {
|
|
|
const fee = getFee(bills.fees, ['common', 'totalFee']);
|
|
|
const feeRate = bills.feeRate && parseFloat(bills.feeRate) !== 0 ? parseFloat(bills.feeRate) : 0;
|
|
|
if (fee && parseFloat(fee) !== 0 && feeRate) {
|
|
|
- bills.calcBase = scMathUtil.roundForObj(parseFloat(fee) * 100 / feeRate, 2);
|
|
|
+ bills.calcBase = scMathUtil.roundForObj(parseFloat(fee) * 100 / feeRate, Decimal.FEE);
|
|
|
} else {
|
|
|
bills.calcBase = fee !== '0' ? fee : '';
|
|
|
}
|
|
@@ -1109,6 +1141,10 @@ const importXML = (() => {
|
|
|
}
|
|
|
// 转换清单
|
|
|
function transformBills(tenderData, billsTemplate) {
|
|
|
+ const rst = {
|
|
|
+ bills: [],
|
|
|
+ billsQuantityDetails: []
|
|
|
+ };
|
|
|
const billsData = mergeBills(tenderData, billsTemplate);
|
|
|
setupFeeCode(billsData);
|
|
|
transformCalcBase(billsData);
|
|
@@ -1128,8 +1164,9 @@ const importXML = (() => {
|
|
|
}
|
|
|
} else {
|
|
|
// 综合合价的小数位数
|
|
|
- const totalFeeDecimal = totalFee.match(/\.\d+/);
|
|
|
- unitFee = scMathUtil.roundForObj(totalFee / bills.quantity, totalFeeDecimal ? totalFeeDecimal[0] : 0);
|
|
|
+ //const totalFeeDecimal = totalFee.match(/\.\d+/);
|
|
|
+ //unitFee = scMathUtil.roundForObj(totalFee / bills.quantity, totalFeeDecimal ? totalFeeDecimal[0] : 0);
|
|
|
+ unitFee = scMathUtil.roundForObj(totalFee / bills.quantity, Decimal.FEE);
|
|
|
}
|
|
|
const commonFee = bills.fees.find(fee => fee.fieldName === 'common');
|
|
|
if (commonFee) {
|
|
@@ -1137,10 +1174,26 @@ const importXML = (() => {
|
|
|
}
|
|
|
}
|
|
|
bills.projectID = tenderData.ID;
|
|
|
- bills.quantityEXP = bills.quantity;
|
|
|
- // TODO 删除items rations feeCode
|
|
|
+ // 工程量明细
|
|
|
+ transformQuantityDetails(tenderData.ID, bills.quantityDetails, bills.ID, 'billID');
|
|
|
+ bills.quantityEXP = bills.quantityDetails && bills.quantityDetails.length ? GCLMXHj : bills.quantity;
|
|
|
+ if (bills.quantityDetails) {
|
|
|
+ rst.billsQuantityDetails.push(...bills.quantityDetails);
|
|
|
+ }
|
|
|
+ rst.bills.push(bills);
|
|
|
});
|
|
|
- return billsData;
|
|
|
+
|
|
|
+ return rst;
|
|
|
+ }
|
|
|
+ // 转换工程量明细数据
|
|
|
+ function transformQuantityDetails(tenderID, quantityDetails, refID, typeKey) {
|
|
|
+ if (quantityDetails) {
|
|
|
+ quantityDetails.forEach(item => {
|
|
|
+ item.ID = uuid.v1();
|
|
|
+ item[typeKey] = refID; // billID、rationID
|
|
|
+ item.projectID = tenderID;
|
|
|
+ });
|
|
|
+ }
|
|
|
}
|
|
|
// 转换人材机汇总相关数据(人材机汇总、承包人材料、评标材料、暂估价材料、组成物、单价文件)
|
|
|
function transformGLJList(tenderData, IDPlaceholder, projectGLJMap) {
|
|
@@ -1184,7 +1237,6 @@ const importXML = (() => {
|
|
|
rst.projectGLJ.push(projectGLJ);
|
|
|
// 单价文件数据:
|
|
|
rst.unitPrice.push(generateUnitPrice(projectGLJ));
|
|
|
- // TODO 删除ratios
|
|
|
});
|
|
|
}
|
|
|
// 转换与项目人材机关联的材料
|
|
@@ -1261,7 +1313,8 @@ const importXML = (() => {
|
|
|
const rst = {
|
|
|
ration: [],
|
|
|
rationGLJ: [],
|
|
|
- rationCoe: []
|
|
|
+ rationCoe: [],
|
|
|
+ rationQuantityDetails: []
|
|
|
};
|
|
|
billsData
|
|
|
.filter(bills => bills.rations && bills.rations.length)
|
|
@@ -1273,12 +1326,17 @@ const importXML = (() => {
|
|
|
ration.projectID = tenderData.ID;
|
|
|
ration.billsItemID = bills.ID;
|
|
|
ration.contain = getContain(bills, ration);
|
|
|
+ // 工程量明细
|
|
|
+ transformQuantityDetails(tenderData.ID, ration.quantityDetails, ration.ID, 'rationID');
|
|
|
+ ration.quantityEXP = getQuantityEXP(bills, ration);
|
|
|
+ if (ration.quantityDetails) {
|
|
|
+ rst.rationQuantityDetails.push(...ration.quantityDetails);
|
|
|
+ }
|
|
|
rst.ration.push(ration);
|
|
|
// 定额人材机
|
|
|
rst.rationGLJ.push(...transformRationGLJs(bills, ration));
|
|
|
// 定额系数
|
|
|
rst.rationCoe.push(generateRationCoe(ration));
|
|
|
- // TODO 删除rationGljs
|
|
|
});
|
|
|
});
|
|
|
return rst;
|
|
@@ -1336,6 +1394,24 @@ const importXML = (() => {
|
|
|
option_list: []
|
|
|
}
|
|
|
}
|
|
|
+ // 获取定额的工程量表达式
|
|
|
+ function getQuantityEXP(bills, ration) {
|
|
|
+ if (ration.quantityDetails && ration.quantityDetails.length) {
|
|
|
+ return GCLMXHj;
|
|
|
+ }
|
|
|
+ // 定额根单位与清单根单位相同,则定额工程量表达式为QDL;否则定额工程量表达式为:定额工程量 * 定额单位量词
|
|
|
+ // eg: 清单单位:m 定额单位:100m
|
|
|
+ const reg = /\d+(\D+.*)/;
|
|
|
+ const billsRootUnit = bills.unit && bills.unit.replace(reg, '$1') || '';
|
|
|
+ const rationRootUnit = ration.unit && ration.unit.replace(reg, '$1') || '';
|
|
|
+ if (billsRootUnit === rationRootUnit) {
|
|
|
+ return QDL;
|
|
|
+ }
|
|
|
+ const numReg = /(\d+)\D+.*/;
|
|
|
+ const num = ration.unit && ration.unit.replace(numReg, '$1') || '1';
|
|
|
+ return ration.quantity * num;
|
|
|
+
|
|
|
+ }
|
|
|
}
|
|
|
// 删除一些无用属性,减少通信数据量
|
|
|
function clean(detailData) {
|
|
@@ -1344,8 +1420,8 @@ const importXML = (() => {
|
|
|
ration,
|
|
|
projectGLJ
|
|
|
} = detailData;
|
|
|
- bills.forEach(item => delete item.items && delete item.rations && delete item.feeCode);
|
|
|
- ration.forEach(item => delete item.rationGLJs);
|
|
|
+ bills.forEach(item => delete item.items && delete item.rations && delete item.feeCode && delete item.quantityDetails);
|
|
|
+ ration.forEach(item => delete item.rationGLJs && delete item.quantityDetails);
|
|
|
projectGLJ.forEach(item => delete item.ratios);
|
|
|
}
|
|
|
// 需要给清单、定额价格字段赋上调价数据,不然打开项目后会被重算: project_view.js -> loadProjectData方法内
|
|
@@ -1366,14 +1442,22 @@ const importXML = (() => {
|
|
|
}
|
|
|
// 转换详细的项目数据,清单、定额、定额人材机、项目人材机、单价文件等
|
|
|
function transformDetail(tenderData, IDPlaceholder, billsTemplate) {
|
|
|
- const bills = transformBills(tenderData, billsTemplate);
|
|
|
+ const { bills, billsQuantityDetails } = transformBills(tenderData, billsTemplate);
|
|
|
// 转换定额的处理依赖转换后的项目人材机数据,因此需要先转换项目人材机相关的数据
|
|
|
const projectGLJMap = {};
|
|
|
const relatedljGLJData = transformGLJList(tenderData, IDPlaceholder, projectGLJMap);
|
|
|
- const relatedRationData = transformRations(tenderData, bills, projectGLJMap);
|
|
|
+ const {
|
|
|
+ ration,
|
|
|
+ rationGLJ,
|
|
|
+ rationCoe,
|
|
|
+ rationQuantityDetails
|
|
|
+ } = transformRations(tenderData, bills, projectGLJMap);
|
|
|
const detailData = {
|
|
|
bills,
|
|
|
- ...relatedRationData,
|
|
|
+ ration,
|
|
|
+ rationGLJ,
|
|
|
+ rationCoe,
|
|
|
+ quantityDetails: [...billsQuantityDetails, ... rationQuantityDetails],
|
|
|
...relatedljGLJData
|
|
|
};
|
|
|
clean(detailData);
|