浏览代码

Merge branch 'master' into olym

olym 7 年之前
父节点
当前提交
3eff2f2fdd

+ 2 - 1
config/gulpConfig.js

@@ -8,7 +8,8 @@ module.exports = {
         'lib/jquery/jquery-3.2.1.min.js',
         'lib/popper/popper.min.js',
         'lib/bootstrap/bootstrap.min.js',
-        'web/building_saas/js/*.js'
+        'web/building_saas/js/*.js',
+        'public/web/scMathUtil.js'
     ],
     common_css:[
         'lib/bootstrap/css/bootstrap.min.css',

+ 19 - 2
modules/fee_rates/controllers/fee_rates_controller.js

@@ -54,7 +54,8 @@ module.exports = {
     getChangeInfo:getChangeInfo,
     changeFeeRateFileFromCurrent:changeFeeRateFileFromCurrent,
     changeFeeRateFileFromOthers:changeFeeRateFileFromOthers,
-    setFeeRateToBill:setFeeRateToBill
+    setFeeRateToBill:setFeeRateToBill,
+    updateFeeRate:updateFeeRate
 }
 
 function libNames(req, res) {
@@ -193,4 +194,20 @@ async function setFeeRateToBill(req,res) {
         result.message = err.message;
     }
     res.json(result);
-}
+}
+
+async function updateFeeRate(req,res) {
+    let result={
+        error:0
+    }
+    try {
+        let data = req.body.data;
+        let uresult= await feeRateFacde.updateFeeRate(data);
+        result.data=uresult;
+    }catch (err){
+        console.log(err);
+        result.error=1;
+        result.message = err.message;
+    }
+    res.json(result);
+}

+ 11 - 9
modules/fee_rates/facade/fee_rates_facade.js

@@ -27,7 +27,8 @@ module.exports={
     changeFeeRateFileFromOthers:changeFeeRateFileFromOthers,
     newFeeRateFile:newFeeRateFile,
     getFeeRatesByProject:getFeeRatesByProject,
-    setFeeRateToBill:setFeeRateToBill
+    getGCFeeRateFiles: getGCFeeRateFiles ,
+    updateFeeRate:updateFeeRate
 };
 let operationMap={
     'ut_create':create_fee_rate,
@@ -42,14 +43,6 @@ let updateFunctionMap = {
     'feeRateFileSaveAs':feeRateFileSaveAs
 }
 
-//测试数据 key projectID, value feeRateFileID
-let project_feeRateF_map={
-    99:'da059df1-7c18-11e7-9e2f-1390b52643b4'
-}
-
-
-
-
 
 function create_fee_rate() {
 
@@ -358,6 +351,11 @@ async function setFeeRateToBill(data){
     return "ok";
 }
 
+async function updateFeeRate(data) {
+    data=JSON.parse(data);
+   return  await feeRateModel.findOneAndUpdate(data.query,data.doc);
+}
+
 async function changeFeeRateFileFromCurrent(jdata){
     let data = JSON.parse(jdata);
     let newFeeRateFile=data.newFeeRateFile;
@@ -397,4 +395,8 @@ async function changeFeeRateFileFromOthers(jdata) {
     newFeeRateFile.rates=newFeeRate.rates;
     newFeeRateFile.usageProjects=await getUsageProjects(newFeeRateFile.ID);
     return newFeeRateFile;
+}
+
+async function getGCFeeRateFiles(userID){
+    return await feeRateFileModel.find({userID: userID, 'deleteInfo.deleted': true});
 }

+ 1 - 1
modules/fee_rates/routes/fee_rates_route.js

@@ -19,7 +19,7 @@ module.exports = function (app) {
     frRouter.post('/changeFeeRateFileFromCurrent', frController.changeFeeRateFileFromCurrent);
     frRouter.post('/changeFeeRateFileFromOthers', frController.changeFeeRateFileFromOthers);
     frRouter.post('/setFeeRateToBill', frController.setFeeRateToBill);
-
+    frRouter.post('/updateFeeRate', frController.updateFeeRate);
     app.use('/feeRates',frRouter);
 }
 

+ 12 - 0
modules/glj/models/unit_price_file_model.js

@@ -125,6 +125,18 @@ class UnitPriceFileModel extends BaseModel {
 
         return result;
     }
+
+    /**
+     * 根据用户获取对应被删除的单价文件
+     *
+     * @param {String} userID
+     * @return {Promise}
+     */
+    async getGCUnitPriceFiles(userID){
+        let condition = {userID: userID, 'deleteInfo.deleted': true};
+        let result = await this.findDataByCondition(condition, null, false);
+        return result;
+    }
 }
 
 export default UnitPriceFileModel;

+ 1 - 0
modules/main/facade/calc_program_facade.js

@@ -88,6 +88,7 @@ function save (user_id, datas, callback) {
 }
 
 function saveCalcItem(dataObj, callback) {
+    dataObj=JSON.parse(dataObj);
     projectCalcProgramsModel.findOne({projectID: dataObj.projectID}, function (err, data) {
         if(!err){
             for (let i = 0; i < data.templates.length; i++){

+ 57 - 0
modules/pm/controllers/pm_controller.js

@@ -190,5 +190,62 @@ module.exports = {
             let responseData = error.err === 1 ? null : [];
             callback(request, response, error.err, error.msg, responseData);
         }
+    },
+    //拼接获取回收站数据
+    getGCDatas: async function(request, response) {
+        let userID = req.session.sessionUser.ssoId;
+        let engIdsSet = new Set(), rootIdsSet = new Set(), rst = [];
+        try{
+            let gc_unitPriceFiles = await ProjectsData.getGCFiles('UnitPriceFile', userID);
+            let gc_feeRateFiles = await ProjectsData.getGCFiles('FeeRateFile', userID);
+            let gc_tenderFiles = await ProjectsData.getGCFiles(projType.tender, userID);
+            if(gc_unitPriceFiles.length > 0){
+                gc_unitPriceFiles.forEach(function (obj) {
+                    rootIdsSet.add(obj.rootProjectID);
+                });
+            }
+            if(gc_feeRateFiles.length > 0){
+                gc_feeRateFiles.forEach(function (obj) {
+                    rootIdsSet.add(obj.rootProjectID);
+                });
+            }
+            if(gc_tenderFiles.length > 0){
+                rst = rst.concat(gc_tenderFiles);
+                gc_tenderFiles.forEach(function (obj) {
+                    engIdsSet.add(obj.ParentID);
+                });
+            }
+            if(engIdsSet.size > 0){
+                let engineerings = await ProjectsData.getProjectsByIds(Array.from(engIdsSet));
+                engineerings.forEach(function (obj) {
+                    rst.push(obj);
+                    rootIdsSet.add(obj.ParentID);
+                });
+            }
+            if(rootIdsSet.size > 0){
+                let projects = await ProjectsData.getProjectsByIds(Array.from(rootIdsSet));
+                for(let i = 0, len = projects.length; i < len; i++){
+                    projects[i].unitPriceFiles = [];
+                    projects[i].feeRateFiles = [];
+                    for(let j = 0, jLen = gc_unitPriceFiles.length; j < jLen; j++){
+                        if(gc_unitPriceFiles[j].rootProjectID === projects[i].ID){
+                            projects[i].unitPriceFiles.push(gc_unitPriceFiles);
+                            break;
+                        }
+                    }
+                    for(let j = 0, jLen = gc_feeRateFiles.length; j < jLen; j++){
+                        if(gc_feeRateFiles[j].rootProjectID === projects[i].ID){
+                            projects[i].feeRateFiles.push(gc_feeRateFiles[j]);
+                            break;
+                        }
+                    }
+                }
+                rst = rst.concat(projects);
+            }
+            callback(request, response, null, 'success', rst);
+        }
+        catch (error){
+            callback(request, response, true, 'fail', null);
+        }
     }
 };

+ 20 - 0
modules/pm/models/project_model.js

@@ -226,6 +226,25 @@ ProjectsDAO.prototype.getProject = function (key, callback) {
     }
 };
 
+ProjectsDAO.prototype.getProjectsByIds = async function (ids){
+    return await Projects.find({ID: {$in: ids}});
+};
+
+ProjectsDAO.prototype.getGCFiles = async function (fileType, userID){
+    let rst;
+    if(fileType === 'UnitPriceFile'){
+        let unitPriceFileModel = new UnitPriceFileModel();
+        rst = await unitPriceFileModel.getGCUnitPriceFiles(userID);
+    }
+    else if(fileType === 'FeeRateFile'){
+        rst = await feeRateFacade.getGCFeeRateFiles(userID);
+    }
+    else {
+        rst = await Projects.find({projType: fileType, 'deleteInfo.deleted': true});
+    }
+    return rst;
+};
+
 /**
  * 整理工程专业对应标准库数据
  *
@@ -345,6 +364,7 @@ ProjectsDAO.prototype.changeUnitPriceFileInfo = async function(projectId, change
     return result.ok === 1;
 };
 
+
 module.exports ={
     project: new ProjectsDAO(),
     projType: projectType

+ 1 - 0
modules/reports/models/rpt_template.js

@@ -16,6 +16,7 @@ let RptTemplateSchema = new Schema({
         "主数据指标_拓展集合": Array,
         "从数据指标_拓展集合": Array
     },
+    "映射数据预处理": Array,
     "布局框_集合": Array,
     "流水式表_信息": Schema.Types.Mixed,
     "流水式表_拓展信息": Schema.Types.Mixed,

+ 1 - 0
modules/reports/rpt_component/jpc_ex.js

@@ -157,6 +157,7 @@ JpcExSrv.prototype.createNew = function(){
                 let expression = me.formulas[i][JV.PROP_EXPRESSION];
                 if (expression) {
                     let $ME = me.formulas[i];
+                    console.log(expression);
                     eval(expression);
                 }
             }

+ 183 - 2
modules/reports/util/rpt_construct_data_util.js

@@ -5,6 +5,10 @@
 let JV = require('../rpt_component/jpc_value_define');
 let $JE = require('../rpt_component/jpc_rte');
 let consts = require('../../../modules/main/models/project_consts');
+
+let fsUtil = require("../../../public/fsUtil");
+
+let treeUtil = require('../../../public/treeUtil');
 let projectConst = consts.projectConst;
 let projectConstList = consts.projectConstList;
 
@@ -86,13 +90,19 @@ class Rpt_Data_Extractor {
         $PROJECT.DETAIL.getRationPropertyByID = ext_getRationPropertyByID;
         if (tpl[JV.NODE_MAP_DATA_HANDLE_INFO]) {
             for (let preHandle of tpl[JV.NODE_MAP_DATA_HANDLE_INFO]) {
+                let srcData = getModuleDataByKey(rawDataObj.prjData, preHandle[JV.PROP_DATA_KEY]);
                 switch(preHandle[JV.PROP_HANDLE_TYPE]) {
                     case JV.PROP_HANDLE_TYPE_SORT:
+                        sortData(srcData, preHandle);
                         break;
                     case JV.PROP_HANDLE_TYPE_FILTER:
+                        filterData(srcData, preHandle, rawDataObj.prjData);
                         break;
                     case JV.PROP_HANDLE_TYPE_SUM:
-                        //
+                        summaryData(srcData, preHandle, rawDataObj.prjData);
+                        break;
+                    default:
+                        break;
                 }
             }
         }
@@ -120,10 +130,181 @@ class Rpt_Data_Extractor {
         assembleFields(tpl[JV.NODE_FIELD_MAP][JV.NODE_DETAIL_FIELDS_EX], rptDataObj[JV.DATA_DETAIL_DATA_EX], $PROJECT);
         // console.log(JV.DATA_DETAIL_DATA_EX);
         // console.log(rptDataObj[JV.DATA_DETAIL_DATA_EX]);
+        return rptDataObj;
     };
 
 }
 
+function getModuleDataByKey(prjData, key) {
+    let rst = null;
+    for (let item of prjData) {
+        if (item.moduleName === key) {
+            rst = item;
+            break;
+        }
+    }
+    return rst;
+}
+
+function summaryData(sourceData, handleCfg, prjData){
+    let rstArr = [], tempRstArr = [];
+    let curParentPrjData = {};
+    for (let item of sourceData.data) {
+        if (item._doc) {
+            tempRstArr.push(item._doc);
+        } else {
+            tempRstArr.push(item);
+        }
+    }
+    let private_get_grp_key = function (item) {
+        let keys = [];
+        for (let cfg of handleCfg[JV.PROP_SUM_GROUP_KEYS]) {
+            if (typeof cfg === "string") {
+                keys.push(item[cfg]);
+            } else {
+                if (!curParentPrjData[cfg["seeking_parent"]]) curParentPrjData[cfg["seeking_parent"]] = getModuleDataByKey(prjData, cfg["seeking_parent"]);
+                for (let pDataItem of curParentPrjData[cfg["seeking_parent"]].data) {
+                    let data = (pDataItem._doc)?pDataItem._doc:pDataItem;
+                    if (item[cfg["seeking_key"]] === data[cfg["parent_key"]]) {
+                        keys.push(data[cfg["parent_grp_key"]]);
+                        break;
+                    }
+                }
+            }
+        }
+        return ( "grp_key_" + keys.join('_'));
+    }
+    let sumObj = {};
+    for (let dtl of tempRstArr) {
+        let grpKey = private_get_grp_key(dtl);
+        if (sumObj[grpKey] === null || sumObj[grpKey] === undefined) {
+            sumObj[grpKey] = dtl;
+            rstArr.push(dtl);
+        } else {
+            for (let sumKey of handleCfg[JV.PROP_SUM_SUM_KEYS]) {
+                if (dtl[sumKey]) {
+                    sumObj[grpKey][sumKey] += dtl[sumKey];
+                }
+            }
+        }
+    }
+    delete sourceData.data;
+    sourceData.data = rstArr;
+    // fsUtil.wirteObjToFile(sourceData.data, "D:/GitHome/ConstructionCost/tmp/sumRst.js");
+}
+
+function filterData(sourceData, handleCfg, prjData) {
+    let rstArr = [], tempRstArr = [];
+    for (let item of sourceData.data) {
+        if (item._doc) {
+            tempRstArr.push(item._doc);
+        } else {
+            tempRstArr.push(item);
+        }
+    }
+    let private_chkVal = function (src, dest, compStr) {
+        let rst = true;
+        switch (compStr) {
+            case "==" :
+                rst = (src == dest);
+                break;
+            case "===" :
+                rst = (src === dest);
+                break;
+            case ">" :
+                rst = (src > dest);
+                break;
+            case ">=" :
+                rst = (src >= dest);
+                break;
+            case "<" :
+                rst = (src < dest);
+                break;
+            case "<=" :
+                rst = (src <= dest);
+                break;
+            case "!=" :
+                rst = (src != dest);
+                break;
+            case "!==" :
+                rst = (src !== dest);
+                break;
+            default:
+                rst = true;
+        }
+        return rst;
+    }
+    for (let item of tempRstArr) {
+        let compRst = true;
+        let curComparePrjData = null;
+        for (let cfg of handleCfg[JV.PROP_FILTER_KEY]) {
+            if (cfg[JV.PROP_FILTER_COMPARE_VAL]) {
+                //比较key值
+                compRst = private_chkVal(item[cfg.key], cfg[JV.PROP_FILTER_COMPARE_VAL], cfg[JV.PROP_FILTER_CONDITION]);
+            } else if (cfg[JV.PROP_FILTER_COMPARE_OBJ] && cfg[JV.PROP_FILTER_COMPARE_OBJ_KEY]){
+                //通过其他对象来过滤
+                if (!curComparePrjData) {
+                    curComparePrjData = getModuleDataByKey(prjData, cfg[JV.PROP_FILTER_COMPARE_OBJ]);
+                }
+                for (let data of curComparePrjData.data) {
+                    compRst = private_chkVal(item[cfg.key], data[cfg[JV.PROP_FILTER_COMPARE_OBJ_KEY]], cfg[JV.PROP_FILTER_CONDITION]);
+                    if (compRst) break;
+                }
+            }
+        }
+        if (compRst) {
+            rstArr.push(item);
+        }
+    }
+    delete sourceData.data;
+    sourceData.data = rstArr;
+    // fsUtil.wirteObjToFile(sourceData.data, "D:/GitHome/ConstructionCost/tmp/filteredRst.js");
+}
+
+function sortData(sourceData, sortCfg) {
+    let rst = sourceData.data, tempRstArr = [];
+    let sortType = sortCfg[JV.PROP_SORT_TYPE];
+    for (let item of sourceData.data) {
+        if (item._doc) {
+            tempRstArr.push(item._doc);
+        } else {
+            tempRstArr.push(item);
+        }
+    }
+    switch (sortType) {
+        case "tree":
+            rst = treeUtil.buildTreeNodeDirectly(tempRstArr);
+            let destArr = [];
+            treeUtil.getFlatArray(rst, destArr);
+            delete sourceData.data;
+            sourceData.data = destArr;
+            // fsUtil.wirteObjToFile(sourceData.data, "D:/GitHome/ConstructionCost/tmp/sortedAndFlattedRst.js");
+            break;
+        case "normal":
+            tempRstArr.sort(function(a, b){
+                let compRst = 0;
+                for (let comp of sortCfg[JV.PROP_SORT_KEYS]) {
+                    let reverse = (comp.order === 'ascend')?1:(-1);
+                    if (a[comp.key] > b[comp.key]) {
+                        compRst = reverse;
+                        break;
+                    } else if (a[comp.key] < b[comp.key]) {
+                        compRst = -reverse;
+                        break;
+                    }
+                }
+                return compRst;
+            });
+            delete sourceData.data;
+            sourceData.data = tempRstArr;
+            // fsUtil.wirteObjToFile(sourceData.data, "D:/GitHome/ConstructionCost/tmp/normalSortedRst.js");
+            break;
+        default:
+            //
+    }
+    return rst;
+}
+
 function setupFunc(obj, prop, ownRawObj) {
     obj[prop] = {};
     obj[prop]["myOwnRawDataObj"] = ownRawObj;
@@ -186,7 +367,7 @@ function ext_getPropety(propKey) {
     let dtObj = parentObj["myOwnRawDataObj"];
     if (propKey && dtObj) {
         for (let dItem of dtObj.data) {
-            let doc = dItem._doc;
+            let doc = (dItem._doc === null || dItem._doc === undefined)?dItem:dItem._doc;
             if (doc.hasOwnProperty("property")) {
                 rst.push(doc["property"][propKey]);
             } else if (doc.hasOwnProperty(propKey)) {

+ 5 - 5
public/scMathUtil.js

@@ -2,16 +2,16 @@
  * Created by Tony on 2017/4/14.
  */
 const fs = require('fs');
-var scMath = null;
+let scMath = null;
 
 getScMathUtil = function() {
     if (!(scMath)) {
-        var data = fs.readFileSync(__dirname + '/web/scMathUtil.js', 'utf8', 'r');
+        let data = fs.readFileSync(__dirname + '/web/scMathUtil.js', 'utf8', 'r');
         //console.log(data);
-        eval(data);
-        scMath = scMathUtil;
+        eval(data + ' scMath = scMathUtil;');
+        //scMath = scMathUtil;
     }
     return scMath;
-}
+};
 
 exports.getUtil = getScMathUtil;

+ 10 - 11
public/treeUtil.js

@@ -2,17 +2,16 @@
  * Created by Tony on 2017/3/14.
  */
 
-const fs = require('fs');
-var treeNodeUtil = null;
+import fs from 'fs';
 
-getTreeNodeUtil = function() {
-    if (!(treeNodeUtil)) {
-        var data = fs.readFileSync(__dirname + '/web/treeDataHelper.js', 'utf8', 'r');
-        //console.log(data);
-        eval(data);
-        treeNodeUtil = tree_Data_Helper;
-    }
-    return treeNodeUtil;
+function getTreeNodeUtil() {
+    let tmpRst = null;
+    let data = fs.readFileSync(__dirname + '/web/treeDataHelper.js', 'utf8', 'r');
+    //console.log(data);
+    eval(data + ' ; tmpRst = tree_Data_Helper; ');
+    return tmpRst;
 }
 
-exports.getUtil = getTreeNodeUtil;
+const treeNodeUtil = getTreeNodeUtil();
+
+module.exports = treeNodeUtil;

+ 8 - 5
public/web/rpt_value_define.js

@@ -45,16 +45,19 @@ const JV = {
     NODE_BIZ_TYPE_SUM: "汇总类型",
     NODE_BIZ_TYPE_DETAIL: "明细类型",
 
-    NODE_MAP_DATA_HANDLE_INFO: "映射数据过滤及统计处理",
+    NODE_MAP_DATA_HANDLE_INFO: "映射数据处理",
     PROP_DATA_KEY: "映射数据对象",
     PROP_HANDLE_TYPE: "预处理类型",
-    PROP_FILTER_KEY: "过滤键属性",
-    PROP_FILTER_DEPENDENT_ON: "过滤依据对象",
-    PROP_FILTER_DEPENDENT_ON_KEY: "过滤依据对象键属性",
-    PROP_FILTER_CONDITION: "条件",
+    PROP_FILTER_KEY: "过滤键值集",
+    PROP_FILTER_COMPARE_OBJ: "compareObjKey",
+    PROP_FILTER_COMPARE_OBJ_KEY: "compareObjIdKey",
+    PROP_FILTER_COMPARE_VAL: "compareValue",
+    PROP_FILTER_CONDITION: "判断条件",
     PROP_HANDLE_TYPE_FILTER: "过滤",
     PROP_HANDLE_TYPE_SUM: "合计",
     PROP_HANDLE_TYPE_SORT: "排序",
+    PROP_SORT_TYPE: "排序方式",
+    PROP_SORT_KEYS: "排序键值集",
     PROP_SUM_GROUP_KEYS: "分组键值集",
     PROP_SUM_SUM_KEYS: "统计键值集",
     PROP_FIELD_EXP_MAP: "mapExpression",

+ 24 - 24
public/web/scMathUtil.js

@@ -2,45 +2,45 @@
  * Created by jimiz on 2017/3/28.
  */
 
-var scMathUtil = {
+let scMathUtil = {
     innerRoundTo: function(num, digit){
-        var lFactor = Math.pow(10, digit);
-        var fOffSet = 0.5;
-        var sign = '';
+        let lFactor = Math.pow(10, digit);
+        let fOffSet = 0.5;
+        let sign = '';
         if (num < 0){
             sign = '-';
             num = Math.abs(num);
         }
-        var result = Math.floor((num / lFactor) + fOffSet).toString();
-        var iLength = result.length;
-        var r1 = result.substring(0, iLength + digit);
-        var r2 = result.substring(iLength + digit, iLength);
+        let result = Math.floor((num / lFactor) + fOffSet).toString();
+        let iLength = result.length;
+        let r1 = result.substring(0, iLength + digit);
+        let r2 = result.substring(iLength + digit, iLength);
         return Number(sign + r1 + '.' + r2);
     },
     floatToBin: function(num) {
         return num.toString(2);
     },
     binToFloat: function(bin) {
-        var result = 0;
-        var iLength = bin.length;
-        var sign = '';
+        let result = 0;
+        let iLength = bin.length;
+        let sign = '';
         if (iLength > 0 && bin[0]==='-'){
             sign = '-';
             bin = bin.substring(1, iLength);
         }
         iLength = bin.length;
-        var iDot = bin.indexOf('.');
+        let iDot = bin.indexOf('.');
         if (iDot >= 0) {
-            for (var i = 0; i < iLength; i++) {
-                var num = Number(bin[i]);
-                var idx = iDot - i;
+            for (let i = 0; i < iLength; i++) {
+                let num = Number(bin[i]);
+                let idx = iDot - i;
                 if (idx === 0) {
                     continue
                 };
                 if (idx > 0) {
                     idx -= 1
                 };
-                var r = Math.pow(2, idx);
+                let r = Math.pow(2, idx);
                 result += num * r;
             }
         }
@@ -50,16 +50,16 @@ var scMathUtil = {
         return sign + result;
     },
     incMantissa: function(bin){
-        var result = bin;
-        var iDot = bin.indexOf('.');
+        let result = bin;
+        let iDot = bin.indexOf('.');
         if (iDot < 0){return result};
-        var iLength = bin.length;
-        for (var i = iLength - 1; i > iDot; i--){
-            var num = Number(bin[i]);
+        let iLength = bin.length;
+        for (let i = iLength - 1; i > iDot; i--){
+            let num = Number(bin[i]);
             if (num === 0){
                 num = 1;
-                var bin1 = bin.substring(0, i);
-                var bin2 = bin.substring(i + 1, iLength);
+                let bin1 = bin.substring(0, i);
+                let bin2 = bin.substring(i + 1, iLength);
                 result = bin1 + num.toString() + bin2;
                 break;
             }
@@ -68,7 +68,7 @@ var scMathUtil = {
         return result;
     },
     roundTo: function(num, digit){
-        var me = this;
+        let me = this;
         return me.innerRoundTo(me.binToFloat(me.incMantissa(me.floatToBin(num))), digit);
     }
 };

+ 62 - 42
public/web/treeDataHelper.js

@@ -3,22 +3,22 @@
  */
 const NODE_ID = "ID", P_ID = "ParentID", NEXT_ID = "NextSiblingID", ADHOC_PRE_ID="Previous_ID", CHILDREN_NODE = "items", SUB_ID = "sub_ids", EMPTY_ID_VAL = -1;
 
-var tree_Data_Helper = {
+let tree_Data_Helper = {
     buildTreeNodeDirectly: function(data) {
-        var me = this, topArr = [], rst = [], tmpNodes = {}, prefix = "id_";
-        private_getTopNode = function (idArr) {
-            var rst = null;
-            for (var i = 0; i < idArr.length; i++) {
-                if (tmpNodes[prefix + idArr[i]][ADHOC_PRE_ID] == EMPTY_ID_VAL) {
+        let topArr = [], rst = [], tmpNodes = {}, prefix = "id_";
+        let private_getTopNode = function (idArr) {
+            let rst = null;
+            for (let i = 0; i < idArr.length; i++) {
+                if (tmpNodes[prefix + idArr[i]][ADHOC_PRE_ID] === EMPTY_ID_VAL) {
                     rst = tmpNodes[prefix + idArr[i]];
                     break;
                 }
             }
             return rst;
-        }
-        private_buildNodeData = function(parentItem, idArr) {
-            var iter = [], nextNode = private_getTopNode(idArr);
-            while (nextNode != null && nextNode != undefined ) {
+        };
+        let private_buildNodeData = function(parentItem, idArr) {
+            let iter = [], nextNode = private_getTopNode(idArr);
+            while (nextNode !== null && nextNode !== undefined ) {
                 if (parentItem) {
                     parentItem[CHILDREN_NODE].push(nextNode);
                 } else {
@@ -27,25 +27,25 @@ var tree_Data_Helper = {
                 iter.push(nextNode);
                 nextNode = tmpNodes[prefix + nextNode[NEXT_ID]];
             }
-            for (var i = 0; i < iter.length; i++) {
+            for (let i = 0; i < iter.length; i++) {
                 private_buildNodeData(iter[i], iter[i][SUB_ID]);
             }
-        }
+        };
 
-        for (var i = 0; i < data.length; i++) {
+        for (let i = 0; i < data.length; i++) {
             tmpNodes[prefix + data[i][NODE_ID]] = data[i];
             data[i][ADHOC_PRE_ID] = EMPTY_ID_VAL;
             data[i][SUB_ID] = [];
             data[i][CHILDREN_NODE] = [];
-            if (data[i][P_ID] == EMPTY_ID_VAL) {
+            if (data[i][P_ID] === EMPTY_ID_VAL) {
                 topArr.push(data[i][NODE_ID]);
             }
         }
-        for (var i = 0; i < data.length; i++) {
-            if (data[i][NEXT_ID] != EMPTY_ID_VAL) {
+        for (let i = 0; i < data.length; i++) {
+            if (data[i][NEXT_ID] !== EMPTY_ID_VAL) {
                 tmpNodes[prefix + data[i][NEXT_ID]][ADHOC_PRE_ID] = data[i][NODE_ID];
             }
-            if (data[i][P_ID] != EMPTY_ID_VAL) {
+            if (data[i][P_ID] !== EMPTY_ID_VAL) {
                 tmpNodes[prefix + data[i][P_ID]][SUB_ID].push(data[i][NODE_ID]);
             }
         }
@@ -55,34 +55,54 @@ var tree_Data_Helper = {
         topArr.length = 0;
         return rst;
     },
-    reSettleRelatedID: function(treeData) {
-        if (treeData && treeData.length > 0) {
-            for (var i = 0; i < treeData[CHILDREN_NODE].length; i++) {
-                var nI = null;
-                if (i < treeData[CHILDREN_NODE].length - 1) {
-                    nI = treeData[CHILDREN_NODE][i+1];
+
+    getFlatArray: function (srcArr, destArr) {
+        let private_put = function (parentItem) {
+            destArr.push(parentItem);
+            if (parentItem.items) {
+                for (let subItem of parentItem.items) {
+                    private_put(subItem);
                 }
-                settleNodeRelatedID(null, nI, treeData[CHILDREN_NODE][i]);
             }
         }
-    },
-    settleNodeRelatedID : function(parentItem, nextItem, node) {
-        if (parentItem) {
-            node[P_ID] = parentItem[NODE_ID];
-        } else {
-            node[P_ID] = EMPTY_ID_VAL;
+        for (let node of srcArr) {
+            private_put(node);
         }
-        if (nextItem) {
-            node[NEXT_ID] = nextItem[NODE_ID];
-        } else {
-            node[NEXT_ID] = EMPTY_ID_VAL;
-        }
-        for (var i = 0; i < node[CHILDREN_NODE].length; i++) {
-            var nI = null;
-            if (i < node[CHILDREN_NODE].length - 1) {
-                nI = node[CHILDREN_NODE][i+1];
-            }
-            private_settleNodeRelatedID(node, nI, node[CHILDREN_NODE][i]);
+        for (let item of destArr) {
+            delete item[CHILDREN_NODE];
+            delete item[SUB_ID];
+            delete item[ADHOC_PRE_ID];
         }
     }
-}
+
+    // reSettleRelatedID: function(treeData) {
+    //     if (treeData && treeData.length > 0) {
+    //         for (let i = 0; i < treeData[CHILDREN_NODE].length; i++) {
+    //             let nI = null;
+    //             if (i < treeData[CHILDREN_NODE].length - 1) {
+    //                 nI = treeData[CHILDREN_NODE][i+1];
+    //             }
+    //             settleNodeRelatedID(null, nI, treeData[CHILDREN_NODE][i]);
+    //         }
+    //     }
+    // },
+    // settleNodeRelatedID : function(parentItem, nextItem, node) {
+    //     if (parentItem) {
+    //         node[P_ID] = parentItem[NODE_ID];
+    //     } else {
+    //         node[P_ID] = EMPTY_ID_VAL;
+    //     }
+    //     if (nextItem) {
+    //         node[NEXT_ID] = nextItem[NODE_ID];
+    //     } else {
+    //         node[NEXT_ID] = EMPTY_ID_VAL;
+    //     }
+    //     for (let i = 0; i < node[CHILDREN_NODE].length; i++) {
+    //         let nI = null;
+    //         if (i < node[CHILDREN_NODE].length - 1) {
+    //             nI = node[CHILDREN_NODE][i+1];
+    //         }
+    //         private_settleNodeRelatedID(node, nI, node[CHILDREN_NODE][i]);
+    //     }
+    // }
+};

+ 79 - 53
test/unit/reports/test_tpl_09_1.js

@@ -2,11 +2,13 @@
  * Created by Tony on 2017/10/18.
  */
 let test = require('tape');
+import JpcEx from "../../../modules/reports/rpt_component/jpc_ex";
 import JV from "../../../modules/reports/rpt_component/jpc_value_define";
 let mongoose = require("mongoose");
 let fileUtils = require("../../../modules/common/fileUtils");
 let path = require('path');
 let dbm = require("../../../config/db/db_manager");
+let rpt_cfg = require('./rpt_cfg');
 dbm.connect();
 let consts = require('../../../modules/main/models/project_consts');
 let projectConsts = consts.projectConst;
@@ -26,7 +28,8 @@ fileUtils.getGlobbedFiles('../../../modules/reports/models/*.js').forEach(functi
 //暂时引入其它模块的model
 require('../../../modules/fee_rates/models/fee_rates');
 // 引入人工系数模块
-require('../../../modules/main/models/labour_coe');
+require('../../../modules/main/models/labour_coe_model');
+require('../../../modules/main/models/calc_program_model');
 
 let fsUtil = require("../../../public/fsUtil");
 
@@ -35,9 +38,7 @@ let projectDataMdl = require('../../../modules/main/models/project');
 let demoPrjId = - 1;
 let demoRptId = 226, pagesize = "A4";
 
-demoPrjId = 469; //QA: 1号教学楼建筑工程
-// demoPrjId = 491; //QA: 2号教学楼建筑工程
-// demoPrjId = 492; //QA: 3号教学楼建筑工程
+demoPrjId = 610; //QA: 建筑工程
 let userId_Leng = 1142; //小冷User Id
 
 let rptTplFacade = require("../../../modules/reports/facade/rpt_template_facade");
@@ -45,66 +46,90 @@ let rptTplDataFacade = require("../../../modules/reports/facade/rpt_tpl_data_fac
 
 import rptDataExtractor from "../../../modules/reports/util/rpt_construct_data_util";
 
-// test('测试 - 获取project数据: ', function (t) {
-//     projectDataMdl.getData(demoPrjId, function (err, message, result) {
-//         if (!err) {
-//             fsUtil.wirteObjToFile(result, "D:/GitHome/ConstructionCost/tmp/ProjectDataFullObject.js");
-//             t.pass('pass succeeded!');
-//             t.end();
-//         } else {
-//             //callback(req, res, err, message, null);
-//             t.pass('pass failed!');
-//             t.end();
-//         }
-//     });
-// });
+let fs = require('fs');
+//设置Date Format函数
+fs.readFile(__dirname.slice(0, __dirname.length - 18) + '/public/web/date_util.js', 'utf8', 'r', function (err, data) {
+    eval(data);
+});
 
-// test('测试 - 获取project部分数据: ', function (t) {
-//     let filter = [];
-//     filter.push(projectConsts.BILLS);
-//     filter.push(projectConsts.RATION);
-//     filter.push(projectConsts.RATION_GLJ);
-//     filter.push(projectConsts.FEERATE);
-//     prjMdl.project.getUserProject(userId_Leng, demoPrjId, function(err, msg, prjObj){
-//         if (!err) {
-//             projectDataMdl.getFilterData(demoPrjId, filter, function (results) {
-//                 if (results) {
-//                     // let newData = [];
-//                     // for (let item of results) {
-//                     //     newData.push(JSON.stringify(item));
-//                     // }
-//                     // fsUtil.writeArrayToFile(newData, "D:/GitHome/ConstructionCost/tmp/getProjectData_partial.js");
-//                     fsUtil.wirteObjToFile(prjObj, "D:/GitHome/ConstructionCost/tmp/getProjectObjectNew.js");
-//                     fsUtil.wirteObjToFile(results, "D:/GitHome/ConstructionCost/tmp/getProjectData_partialNew.js");
-//                     t.pass('pass succeeded!');
-//                     t.end();
-//                 } else {
-//                     //callback(req, res, err, message, null);
-//                     t.pass('get project data failed!');
-//                     t.end();
-//                 }
-//             });
-//         } else {
-//             t.pass('get project failed!');
-//             t.end();
-//         }
-//     });
-// });
+/*/
+test('测试 - 获取project数据: ', function (t) {
+    projectDataMdl.getData(demoPrjId, function (err, message, result) {
+        if (!err) {
+            fsUtil.wirteObjToFile(result, "D:/GitHome/ConstructionCost/tmp/ProjectDataFullObject.js");
+            t.pass('pass succeeded!');
+            t.end();
+        } else {
+            //callback(req, res, err, message, null);
+            t.pass('pass failed!');
+            t.end();
+        }
+    });
+});
+//*/
+/*/
+test('测试 - 获取project部分数据: ', function (t) {
+    let filter = [];
+    filter.push(projectConsts.BILLS);
+    filter.push(projectConsts.RATION);
+    filter.push(projectConsts.RATION_GLJ);
+    filter.push(projectConsts.FEERATE);
+    prjMdl.project.getUserProject(userId_Leng, demoPrjId, function(err, msg, prjObj){
+        if (!err) {
+            projectDataMdl.getFilterData(demoPrjId, filter, function (results) {
+                if (results) {
+                    // let newData = [];
+                    // for (let item of results) {
+                    //     newData.push(JSON.stringify(item));
+                    // }
+                    // fsUtil.writeArrayToFile(newData, "D:/GitHome/ConstructionCost/tmp/getProjectData_partial.js");
+                    fsUtil.wirteObjToFile(prjObj, "D:/GitHome/ConstructionCost/tmp/getProjectObjectNew.js");
+                    fsUtil.wirteObjToFile(results, "D:/GitHome/ConstructionCost/tmp/getProjectData_partialNew.js");
+                    t.pass('pass succeeded!');
+                    t.end();
+                } else {
+                    //callback(req, res, err, message, null);
+                    t.pass('get project data failed!');
+                    t.end();
+                }
+            });
+        } else {
+            t.pass('get project failed!');
+            t.end();
+        }
+    });
+});
+//*/
 
+//*
 test('测试 - 测试模板啦: ', function (t) {
-    rptTplFacade.getRptTemplate(demoRptId).then(function(tpl) {
+    rptTplFacade.getRptTemplate(demoRptId).then(function(rptTpl) {
         let rptDataUtil = new rptDataExtractor();
-        rptDataUtil.initialize(tpl);
+        rptDataUtil.initialize(rptTpl._doc);
         let filter = rptDataUtil.getDataRequestFilter();
         console.log(filter);
         //正常应该根据报表模板定义的数据类型来请求数据
         rptTplDataFacade.prepareProjectData(userId_Leng, demoPrjId, filter, function (err, msg, rawDataObj) {
             if (!err) {
-                rptDataUtil.assembleData(rawDataObj);
+                let tplData = rptDataUtil.assembleData(rawDataObj);
+                // fsUtil.wirteObjToFile(rawDataObj, "D:/GitHome/ConstructionCost/tmp/rptTplRawDataObject.js");
+                //it's time to build the report!!!
+                let printCom = JpcEx.createNew();
+                rptTpl[JV.NODE_MAIN_INFO][JV.NODE_PAGE_INFO][JV.PROP_PAGE_SIZE] = pagesize;
+                let defProperties = rpt_cfg;
+                let dftOption = JV.PAGING_OPTION_NORMAL;
+                printCom.initialize(rptTpl);
+                printCom.analyzeData(rptTpl, tplData, defProperties, dftOption);
+                let maxPages = printCom.totalPages;
+                let pageRst = printCom.outputAsSimpleJSONPageArray(rptTpl, tplData, 1, maxPages, defProperties);
+                if (pageRst) {
+                    fsUtil.wirteObjToFile(pageRst, "D:/GitHome/ConstructionCost/tmp/testBuiltPageResult.js");
+                } else {
+                    console.log("oh! no pages were created!")
+                }
+
                 t.pass('pass succeeded!');
                 t.end();
-                //fsUtil.wirteObjToFile(rawDataObj, "D:/GitHome/ConstructionCost/tmp/rptTplRawDataObject1.js");
-                //准备执行公式需要的对象
             } else {
                 console.log(msg);
                 t.pass('pass with error!');
@@ -113,6 +138,7 @@ test('测试 - 测试模板啦: ', function (t) {
         })
     });
 });
+//*/
 
 test('close the connection', function (t) {
     setTimeout(function () {

+ 1 - 1
web/building_saas/main/html/calc_program_manage.html

@@ -9,7 +9,7 @@
 
 <body>
 <div style="">
-    <img id="f_btn" src="/web/dest/css/img/feeRate_btn.jpg" alt="" />
+    <img id="f_btn" src="/web/dest/css/img/feeRate_btn.jpg" alt="" style="display: none" />
 </div>
     <div class="toolsbar px-1">
     </div>

+ 47 - 0
web/building_saas/main/js/models/fee_rate.js

@@ -247,6 +247,50 @@ var FeeRate = {
                 }
             }
         };
+
+        FeeRate.prototype.updateFeeRateFromCalc=function (value,editInfo) {
+            var value= number_util.checkNumberValue(value,feeRate_consts.decimal);
+            if(value){
+                if(editInfo.calcItem.feeRateID){
+                    var rate = projectObj.project.FeeRate.getFeeRateByID(editInfo.calcItem.feeRateID);
+                    if(rate!=undefined){
+                        this.updateFeeRateByCalc(rate,value,editInfo);
+                        return;
+                    }
+                }
+                editInfo.calcItem.feeRate=value;
+                editInfo.calcItem.feeRateID=null;
+                var data={'projectID': projectObj.project.ID(),'templatesID': editInfo.template.ID,'calcItem': editInfo.calcItem};
+                rationPM.saveCalcItem(data,function (result) {
+                    rationPM.refreshDetailSheet();
+                })
+                //updateCal
+            }else {
+                rationPM.refreshDetailSheet();
+            }
+        };
+        FeeRate.prototype.updateFeeRateByCalc=function (rate,value,editInfo) {
+            var me=this;
+            var data={
+                query:{
+                    'ID':this.getActivateFeeRateID(),
+                    'rates.ID':rate.ID
+                },
+                doc:{
+                    'rates.$.rate':value
+                }
+            }
+            CommonAjax.post('/feeRates/updateFeeRate', data, function (data) {
+                _.forEach(editInfo.template.calcItems,function (item) {
+                    if(item.feeRateID==rate.ID){
+                        item.feeRate = value;
+                    }
+                })
+                rate.rate=value;
+                rationPM.refreshDetailSheet();
+                socket.emit('feeRateChangeNotify', me.getActivateFeeRateFileID());
+            });
+        }
         FeeRate.prototype.refreshBillsByRateID=function(rate,value){
             rate.rate=value;
             var nodes = _.filter(projectObj.project.mainTree.items,function (n) {
@@ -324,6 +368,9 @@ var FeeRate = {
                 }
             this.setFeeRateToBill(data,callback);
         };
+
+       
+
         FeeRate.prototype.setFeeRateToBill=function(data,callback){
             CommonAjax.post('/feeRates/setFeeRateToBill', data, function (data) {
                 callback(data);

+ 31 - 21
web/building_saas/main/js/views/calc_program_manage.js

@@ -25,7 +25,7 @@ let rationPM = {
             {headerName:"费用名称",headerWidth:200,dataCode:"name", dataType: "String"},
             {headerName:"计算基数",headerWidth:180,dataCode:"dispExpr", dataType: "String"},
             {headerName:"基数说明",headerWidth:300,dataCode:"statement", dataType: "String"},
-            {headerName:"费率",headerWidth:80,dataCode:"feeRate", dataType: "Number",hAlign: "left"},
+            {headerName:"费率",headerWidth:80,dataCode:"feeRate", dataType: "Number",hAlign: "left",tofix:feeRate_consts.decimal},
             {headerName:"字段名称",headerWidth:140,dataCode:"displayFieldName", dataType: "String", hAlign: "center"},
             {headerName:"备注",headerWidth:100,dataCode:"memo", dataType: "String"}
         ],
@@ -56,12 +56,12 @@ let rationPM = {
 
         me.mainSpread.getSheet(0).bind(GC.Spread.Sheets.Events.EnterCell, me.onMainEnterCell);
         me.detailSpread.getSheet(0).bind(GC.Spread.Sheets.Events.CellChanged, me.onDetailCellChanged);
-        //me.detailSpread.getSheet(0).bind(GC.Spread.Sheets.Events.CellClick, me.onCellClick);
+        me.detailSpread.getSheet(0).bind(GC.Spread.Sheets.Events.EditEnded, me.onEditEnded);
         let mSheet = me.mainSpread.getSheet(0);
         sheetCommonObj.showData(mSheet, me.mainSetting, me.datas);
 
         let dSheet = me.detailSpread.getSheet(0);
-        feeRateObject.setFeeRateCellCol(dSheet,4);
+        feeRateObject.setFeeRateCellCol(dSheet,_.findIndex(me.detailSetting.header,{'dataCode':'feeRate'}));
         dSheet.name('calc_detail');
         sheetCommonObj.showData(dSheet, me.detailSetting, me.datas[0].calcItems);
 
@@ -76,30 +76,25 @@ let rationPM = {
         sheetCommonObj.showData(dSheet, me.detailSetting, dData);
         me.detailSpread.resumePaint();
     },
-
-    saveCalcItem: function (projectID, templatesID, calcItem) {
+    onEditEnded: function(sender, args) {
+        var me = rationPM;
+        if(me.detailSetting.header[args.col].dataCode=='feeRate'){
+            var editInfo= me.getSelectionInfo();
+            projectObj.project.FeeRate.updateFeeRateFromCalc(args.editingText,editInfo);
+        }
+    },
+    saveCalcItem: function (data,callback) {//data
         let me = this;
-/*        let projectID = projectInfoObj.projectInfo.ID,
-            templatesID = me.datas,
-            calcItem = {
-                "ID" : 99,
-                "code" : "test",
-                "name" : "testName",
-                "fieldName" : "direct",
-                "dispExpr" : "F2+F5+F6+F10",
-                "expression" : "@('2') + @('5') + @('6') + @('10')",
-                "compiledExpr" : "",
-                "statement" : "基价人工费+基价材料费+基价机械费+未计价材料费"
-            };*/
-
         $.ajax({
-            type: 'post',
+            type: 'POST',
             url: '/calcProgram/saveCalcItem',
-            data: {projectID: projectID, templatesID: templatesID, calcItem: calcItem},
+            data: {'data':JSON.stringify(data)},
             dataType: 'json',
             success: function (result) {
                 if(!result.error){
-                    alert('成功:' + result.message);
+                    if(callback){
+                        callback(result);
+                    }
                 }
                 else{
                     alert('失败:' + result.message);
@@ -107,6 +102,21 @@ let rationPM = {
             }
         })
     },
+    getSelectionInfo:function () {
+        var templateIndex = this.mainSpread.getActiveSheet().getActiveRowIndex();
+        var dIndex = this.detailSpread.getActiveSheet().getActiveRowIndex();
+        var info = {
+            template:this.datas[templateIndex],
+            calcItem:this.datas[templateIndex].calcItems[dIndex]
+        }
+        return info;
+    },
+    refreshDetailSheet:function () {
+        var me=this;
+        var mainSheetIndex = me.mainSpread.getActiveSheet().getActiveRowIndex();
+        sheetCommonObj.showData(me.detailSpread.getSheet(0), me.detailSetting,me.datas[mainSheetIndex].calcItems);
+    }
+
 };
 
 $(document).ready(function(){

+ 14 - 1
web/building_saas/main/js/views/fee_rate_view.js

@@ -640,11 +640,24 @@ var feeRateObject={
             $("#fee_rate_tree").modal('hide');
         });
     },
+    submitFeeRateFromCalc:function () {
+        var rate = feeRateObject.feeRateSelection;
+        var calInfo = rationPM.getSelectionInfo();
+        calInfo.calcItem.feeRateID=rate.ID;
+        calInfo.calcItem.feeRate=null;
+        var data={'projectID': projectObj.project.ID(),'templatesID': calInfo.template.ID,'calcItem': calInfo.calcItem};
+        rationPM.saveCalcItem(data,function (result) {
+            calInfo.calcItem.feeRate=rate.rate;
+            rationPM.refreshDetailSheet();
+            $("#fee_rate_tree").modal('hide');
+        });
+        console.log(calInfo);
+    },
     submitFeeRateBySelect:function () {
         var validate = this.checkSelectedFeeRate();
         if(validate){
             if($('#edit_from').val()=='calc_detail'){
-                //do calc_detail
+                this.submitFeeRateFromCalc();
             }else {
                 this.submitFeeRateFromBill();
             }

+ 1 - 1
web/building_saas/main/js/views/glj_view.js

@@ -301,7 +301,7 @@ var gljOprObj = {
         if(args.row>=me.sheetData.length){
             return;
         }
-        if(me.setting.header[args.col].dataCode=='marketPriceAdjust'){//市场单价调整
+        if(me.setting.header[args.col]&&me.setting.header[args.col].dataCode=='marketPriceAdjust'){//市场单价调整
             var type = me.sheetData[args.row].shortName;
             var index= _.indexOf(me.setting.notEditedType,type);
             if(index!=-1){

+ 1 - 0
web/common/html/header.html

@@ -61,4 +61,5 @@
 <script src="/lib/jquery/jquery-3.2.1.min.js"></script>
 <script type="text/javascript" src="/web/building_saas/js/moment.min.js"></script>
 <script type="text/javascript" src="/web/building_saas/js/message.js"></script>
+<script type="text/javascript" src="/public/web/scMathUtil.js"></script>
 <!-- endinject -->

+ 1 - 0
web/users/html/login.html

@@ -69,6 +69,7 @@
     </div>
     <!-- JS. -->
     <!-- inject:js -->
+    <script type="text/javascript" src="/public/web/scMathUtil.js"></script>
     <script src="/lib/jquery/jquery-3.2.1.min.js"></script>
     <script src="/public/web/url_util.js"></script>
     <script src="/lib/popper/popper.min.js"></script>