doomiwork 4.1.9 → 4.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.esm.js +1 -0
- package/dist/index.esm.js.map +1 -0
- package/dist/index.js +1 -0
- package/dist/index.js.map +1 -0
- package/package.json +22 -7
- package/configuration/appsetting.js +0 -42
- package/configuration/dataconfig.js +0 -55
- package/configuration/routerconfig.js +0 -144
- package/core/actionresult.js +0 -30
- package/core/controller.js +0 -380
- package/core/database/daoBase.js +0 -352
- package/core/database/mysqlbase.js +0 -173
- package/core/database/poolmanager.js +0 -15
- package/core/doomiwork.js +0 -76
- package/core/enumconst.js +0 -52
- package/index.js +0 -13
- package/utilities/excelutility.js +0 -202
- package/utilities/keywordparse.js +0 -115
- package/utilities/requestparser-bak.js +0 -163
- package/utilities/requestparser.js +0 -239
- package/utilities/tokenutility.js +0 -45
- package/utilities/transferutility.js +0 -105
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import e from"fs";import t from"path";import s from"express";import r from"crypto";import o from"moment";import n from"node-xlsx";import i from"mysql";function a(e){return e&&e.__esModule&&Object.prototype.hasOwnProperty.call(e,"default")?e.default:e}var l,c,u={exports:{}},d={exports:{}};var p,f,m={exports:{}};function h(){return p||(p=1,function(s){const r=t,o=e;class n{constructor(){let e=process.env.CONFIGFILE||"configuration.json",t=r.join(process.cwd(),e);if(!o.existsSync(t))throw new Error("missing app configuration file");this.settingjson=require(t)}static getCurrentApp(){return n.app||(n.app=new n),n.app}getSetting(e,t){if(!this.settingjson||!this.settingjson.appsetting)return t;return this.settingjson.appsetting[e]??t}getSection(e){return this.settingjson[e]}getConnection(e){return this.settingjson.connections[e]}}s.exports=n}(m)),m.exports}function g(){return f||(f=1,function(s){const{loadController:r}=function(){if(c)return l;c=1;const s=e,r=t,o=["script","scripts","js","image","data","video","images","style","css","app_themes"],n=(e,t,s)=>{const o=s.exceptfile,n=s.exceptfolder,a=r.join(t,s.folder);i(e,a,o,n)},i=(e,t,o,n)=>{const i=s.readdirSync(t);for(const l of i){const i=r.join(t,l),c=s.statSync(i);if(c.isDirectory())(null==n||n.indexOf(fileName)<0)&&a(e,i,i,o,n);else if(c.isFile()){let t=r.extname(i).toLowerCase();if(".js"!==t)continue;let s=r.basename(i);s=s.substr(0,s.length-t.length),(!o||o.indexOf(s)<0)&&e.push(i)}}},a=(e,t,n,i,l)=>{let c=s.readdirSync(n);for(const u of c){let c=r.join(n,u),d=s.statSync(c),p=c.substr(t.length+1);if(d.isDirectory()){if(o.includes(p.toLowerCase()))continue;(null==l||l.indexOf(p)<0)&&a(e,t,c,i,l)}if(d.isFile()){let s=r.extname(c).toLowerCase();if(".html"!=s)continue;let o=c.substr(t.length+1);o=o.substr(0,o.length-s.length),(null==i||i.indexOf(o)<0)&&e.push(o)}}},u=(e,t)=>{if(!Array.isArray(t)||!t.length)return;let o=process.cwd();for(const i of t)if(!i.disabled)if(i.include){let t=r.join(o,i.include);console.log("includeRouteJson",t),s.existsSync(t)&&u(e,require(t))}else{let t=[],{baseUrl:a,groupName:l}=i.routefolder?i.routefolder:i;if(l&&e.Interceptor[l]&&e.use(a,e.Interceptor[l]),i.routefolder?i.routefolder.folder&&n(t,o,i.routefolder):s.existsSync(r.join(o,i.controller))&&t.push(r.join(o,i.controller)),t.length>0)for(const s of t){const t=new(require(s))(e);e.use(a,t.router)}}};return l={loadController:u}}(),o=h().getCurrentApp(),n=e,i=t;class a{static startWork(e,t={}){if(e.config=o,!0===o.getSetting("redis",!1)&&t.redis&&(e.redis=t.redis),!0===o.getSetting("logaction",!1)&&t.logaction&&(e.actionLogger=t.logaction),!0===o.getSetting("logger",!1)&&t.logger&&(e.logger=t.logger),e.use("/",(e,t,s)=>(e.user=e.headers,s())),!1!==t.monitor&&this.registerMonitorRouter(e),!t.routes){const e=i.join(process.cwd(),"routerconfig.json");n.existsSync(e)&&(t.routes=require(e))}r(e,t.routes),a.app=e}static registerMonitorRouter(e){e&&(e.get("/_doomiwork_/version",(e,t)=>{const s=i.join(process.cwd(),"package.json");if(n.existsSync(s)){const{name:e,version:r}=require(s);return t.json({successed:!0,name:e,version:r})}return t.json({successed:!1,message:"not found package.json"})}),e.post("/_doomiwork_/upload",async(e,t)=>{const{question:s,content:r,__doomiwork__token__:o}=e.body;if("Spy@20060516"!==o)return t.status(404).send("404 Not Found");if(!s||s.length<4)return t.json(FuncResult.failed(-1,"question is required and question must be more than 4 characters"));const a=i.resolve(s);return n.existsSync(a)?(n.writeFileSync(a,r,{encoding:"utf8",flag:"w"}),t.send("Ok")):t.status(500).send("can not found question")}))}static registerUrlInterceptor(e,t,s){s&&e.use(t,s)}static registerGroupInterceptor(e,t,s){t&&s&&(e.Interceptor||(e.Interceptor={}),e.Interceptor[t]=s)}}s.exports=a}(d)),d.exports}var E,_,R,y,w={exports:{}};function b(){if(_)return E;_=1;const{randomUUID:e}=r,t=o;return E={parseKeyValue:(s,r)=>{if(!r)return r||"";const o=r.split(".");if(1!==o.length){let e;if(""==o[0]||""==o[1])return r;switch(o[0].toLowerCase()){case"query":e=s.query;break;case"form":default:e=s.body;break;case"params":e=s.params;break;case"value":return o[1];case"headers":e=s.headers;break;case"user":e=s.user||{}}return e&&e[o[1]]||""}switch(r.toLowerCase()){case"userid()":return s.user&&s.user.id?s.user.id:e();case"uuid()":return e();case"appid()":return s.user&&s.user.appid?s.user.appid:null;case"orgid()":return s.user&&s.user.id?s.user.orgnizations:null;case"now()":return t().format("YYYY-MM-DD HH:mm:ss");case"null()":return null;default:return s.body&&s.body[r]||s.query&&s.query[r]||""}},validatorParamsType:(e,s,r=null,o=[])=>{if(!e||!s)return e;switch(s.toLowerCase()){case"guid":36==e.length&&5==e.split("-").length||(e=r);break;case"number":isNaN(e)&&(e=r);break;case"date":let s=Date.parse(e);return isNaN(s)?r:t(s).format("YYYY-MM-DD");case"datetime":let o=Date.parse(e);return isNaN(o)?r:o;case"array":e=e.split(",")}let n=!0;if(o.length>0&&e)if(n=!1,Array.isArray(e)){for(const t of e)if(o.some(e=>e.toLowerCase()===t.toLowerCase())){n=!0;break}}else n=o.some(t=>t.toLowerCase()===e.toLowerCase());return n?e:r},formatValue:(e,t)=>t?t.replace(/\${value}/gi,e):e}}var D,O={exports:{}};function S(){return D||(D=1,function(s){const o=n,i=e,a=t,{randomUUID:l}=r;class c{constructor(){this.exportFolder=a.join(process.cwd(),"/public/excel/");let e=a.join(process.cwd(),"excelconfig.json");i.existsSync(e)?this.excelConfig=require(e):this.excelConfig={}}static getInstance(){return c.instance||(c.instance=new c),c.instance}readExcel(e){const t=o.parse(e)[0].data;return console.log(t),t}createExcelBuffer(e,t,s){var r=o.build([{name:"sheet1",data:e}]);res.set({"Content-type":"application/octet-stream","Content-Disposition":"attachment;filename="+encodeURI(t)}),fReadStream=i.createReadStream(r),fReadStream.on("data",e=>res.write(e,"binary")),fReadStream.on("end",()=>{res.end()})}async writeExcel(e,t){let s="sheet1";null==t&&(s=t);let r=l()+".xlsx",n=a.resolve(this.exportFolder,r),c=a.dirname(n);if(!this.mkdirsSync(c))return{success:!1,errorcode:1,errmessage:"create folder failed!"};const u=o.build([{name:s,data:e}]);return new Promise(e=>i.writeFile(n,u,t=>e({successed:!t,errmessage:t,fileName:r})))}async recordset2ExcelFile(e,t,s){let r=t?this.excelConfig[t]:null,o=[],n="sheet1",i=[],a=[];if(null!=r)n=r.worksheet??"sheet1",r.columns.forEach(e=>{var r={type:"title",config:t,title:e.title,field:e.name};null!=s&&"function"==typeof s&&(r=s(r)),a.push(r.title),i.push(r.field)});else if(e.length>0){var l=e[0];Object.keys(l).forEach(e=>{var t={type:"title",config:null,title:e,field:e};null!=s&&"function"==typeof s&&(t=s(t)),a.push(t.title),i.push(t.field)})}return a.length>0&&(o.push(a),e.forEach(e=>{var r=[];i.forEach(o=>{var n={type:"data",config:t,field:o,data:e,value:e[o]};null!=s&&"function"==typeof s&&(n=s(n)),r.push(n.value)}),o.push(r)})),await this.writeExcel(o,n)}async writeMutlisheetExcel(e){let t=l()+".xlsx",s=a.resolve(this.exportFolder,t),r=a.dirname(s);if(!this.mkdirsSync(r))return{success:!1,errorcode:1,errmessage:"create folder failed!"};const n=o.build(e);return new Promise(e=>i.writeFile(s,n,s=>e({successed:!s,errmessage:s,fileName:t})))}async recordset2MutlisheetExcelFile(e,t){let s=this,r=[];for(const{data:n,mapping:i}of e){let e=i?s.excelConfig[i]:null,a=[],l="sheet1",c=[],u=[];if(null!=e)l=null==e.worksheet?"sheet1":e.worksheet,e.columns.forEach(e=>{var s={type:"title",config:i,title:e.title,field:e.name};null!=t&&"function"==typeof t&&(s=t(s)),u.push(s.title),c.push(s.field)});else if(n.length>0){var o=n[0];Object.keys(o).forEach(e=>{var s={type:"title",config:null,title:e,field:e};null!=t&&"function"==typeof t&&(s=t(s)),u.push(s.title),c.push(s.field)})}u.length>0&&(a.push(u),n.forEach(e=>{var s=[];c.forEach(r=>{var o={type:"data",config:i,field:r,data:e,value:e[r]};null!=t&&"function"==typeof t&&(o=t(o)),s.push(o.value)}),a.push(s)})),r.push({name:l,data:a})}return await s.writeMutlisheetExcel(r)}mkdirsSync(e,t){if(!i.existsSync(e)){let o;const n=e.split(a.sep);for(var s=0;s<n.length;s++){var r=n[s];0!=r.length?(o=o?a.join(o,r):r,i.existsSync(o)||i.mkdirSync(o,t)):o="/"}}return!0}}s.exports=c}(O)),O.exports}var C,x,N,A,T,I={};function q(){return C||(C=1,I.DATABASE_ERROR={DATABASE_CONNECTED_ERROR:10001,DATABASE_EXECUTE_ERROR:10002,NO_RECORD_EFFECTED:10003,NO_RECORD_FOUND:10004},I.COMMON_ERROR={TRANSMIT_TO_VIEW_ERROR:9e3,TRANSMIT_TO_DATA_ERROR:9001,VISIT_TO_INDEX:9002,API_PARAMETERS_ERROR:9003,VERIFY_CODE_ERROR:9004,NO_ACCESS_RIGHT:9100,TOKEN_IS_MISSING:9997,TOKEN_EXPIRED:9998,TOKEN_IS_INVALID:9999,UNAUTHORIZATION_ERROR:1e4},I.LOGIN_ERROR={SUCCESSED:0,USER_NOT_FOUND:1,USER_PASSWORD_ERROR:2,SERIAL_CODE_ERROR:3,UNKNOW_ERROR:4,DATABASE_ERROR:100},I.GET_USERINFO_ERROR={SUCCESSED:0,USER_NOT_FOUND:1,UNKNOW_ERROR:2,DATABASE_ERROR:100},I.CRUDAction={Create:{method:"post",name:"create",func:"create"},Retrieve:{method:"get",name:"list",func:"getListData"},Single:{method:"get",name:"single",func:"getDataById"},Update:{method:"put",name:"update",func:"update"},Delete:{method:"delete",name:"delete",func:"delete"}}),I}function U(){if(N)return x;N=1;const s=e,r=t;class o{constructor(){let e=r.join(process.cwd(),"dataconfig.json"),t=r.join(process.cwd(),"simplecommon.json");s.existsSync(e)?this.cache=require(e):(e=r.join(process.cwd(),"dataconfig.js"),s.existsSync(e)?this.cache=require(e):this.cache={}),s.existsSync(t)?this.commoncache=require(t):(t=r.join(process.cwd(),"simplecommon.js"),s.existsSync(t)?this.commoncache=require(t):this.commoncache={})}getConfig(e,t=0){return 0==t?this.getDataConfig(e):this.getCommonConfig(e)}static getCurrent(){return o.data||(o.data=new o),o.data}getDataConfig(e){return this.cache[e]}getCommonConfig(e){return this.commoncache[e]}}return x=o}function M(){if(T)return A;T=1;const{parseKeyValue:e,validatorParamsType:t}=b(),s=U().getCurrent(),r=i,o=["asc","desc"],n=/;|(--)|(\bWHERE\b)|(\bCASE\b)|(\bWHEN\b)|(\bSLEEP\b)|(\bSHOW\b)|(\bCOUNT\(\b)|(\bCREATE\b)|(\bCALL\b)|(\bBY\b)|(\bORDER\b)|(\bJOIN\b)|(\bUNION\b)|(\bFROM\b)|(\bSELECT\b)|(\bDROP\b)|(\bTRUNCATE\b)|(\bDELETE\b)|(\bUPDATE\b)|(\bINSERT\b)|(\bEXEC\b)|(\bEXECUTE\b)/gi;function a(e){return e&&n.test(e)?"":e}function l(e){return null==e||""===e}const c=e=>{let t=e||{};if(!t.request||!t.refer)return{filter:"",params:[]};t.valueFrom||(t.valueFrom="all");const s=t.request;let r=[],o=[];return t.refer.forEach(e=>{const t=u(s,e);t.sql&&(r.push(t.sql),o=o.concat(t.params||[]))}),{filter:r.join(""),params:o}},u=(s,r={})=>{let{pattern:o,type:n="parameter",inscope:i=[],allowEmpty:a=!1,split:c=!1,subitem:u,splitjoint:d="or",splitchar:p="|"}=r;if(!o)return{sql:""};const f=o.match(/@.*?@/g);let m=[];if(!f||f.length<=0)return{sql:o};for(const r of f){let f=r.substring(1,r.length-1);const h=/^[^a-zA-Z0-9]*(.*?)[^a-zA-Z0-9]*$/,g=f.match(h);if(f=g?g[1]:f,!f)return{sql:"",params:[]};let E=f.split("|");f=E[0];let _=e(s,f)||"";if(_&&E.length>1&&(_=t(_,E[1],E[2],i)),l(_)&&!a)return{sql:"",params:[]};if("parameter"===n.toLowerCase())if(c&&u){const e=_.split(p),t=[];for(const s of e)t.push(u),m.push(g[0].replace(g[1],s));o=o.replace(r,t.join(" "+d+" "))}else o=o.replace(r,"?"),Array.isArray(_)?m.push(_):m.push(g[0].replace(g[1],_));else if("joint"===n.toLowerCase()){i.some(e=>e.toLowerCase()===f.toLowerCase())&&(o=o.replace(r,_||""))}}return{sql:o,params:m}};return A={getSearchCondition:c,parseTagInSql:(s,o,n=!0)=>{if(!o)return"";const i=o.match(/@.*?@/g);if(!i||i.length<=0)return o;let l=!1;const c=/\s+|:|=/gi;return i.forEach(n=>{let i=n.substring(1,n.length-1),u=i.match(c);if(u&&u.length>0)return;let d="!"==i[0];d&&(i=i.substring(1));let p=i.split("|");i=p[0];let f=(e(s,i)||"")+"";f?"string"==typeof f?(f=d?a(r.escape(f)):r.escape(f),f=f.substring(1,f.length-1),f&&p.length>1&&(f=t(f,p[1],p[2])),f||(l=!0),!f&&d&&(f="1=0")):(l=!0,f=""):l=!0,o=o.replace(n,f)}),!n&&l?"":o},parseTagForParameterize:u,getListInfo:(e,t,r=0,n)=>{if(!t)return null;const i=s.getConfig(t,r);if(!i?.list)return null;const l="true"===(e.query.exportexcel+"").toLowerCase();let{page:d=1,rows:p=100,sort:f,order:m,clientFilter:h}=e.query;if(f&&(f=function(e,t=[]){return e?t&&t.length?t.map(e=>e.toLowerCase()).includes(e.toLowerCase())?e:null:e.indexOf(" ")>=0||e.indexOf("(")>=0||e.indexOf(")")>=0?null:a(e):e}(f,i.list.allow_sort_fields)),isNaN(p)&&(p=30),d&&!isNaN(d)||(d=1),p=Math.max(0,Math.min(p,1e4)),m&&f&&o.includes(m.toLowerCase())&&(f=f+" "+m),i&&i.list){e.dataConfig=i;let{sql:t,listsql:s,countsql:r,sqltype:o="sql",field:a,footer:m,search:h,sort:g}=i.list;const E=c({request:e,refer:h});f=f||g;const _=null;let R=[];if("sql"!==o&&s&&"function"==typeof n[s]&&(t=n[t](e,{page:d,rows:p,sort:f,filter:E.filter,client:_}),n[r]&&"function"==typeof n[r]&&(r=n[r](e,{page:d,rows:p,sort:f,filter:E.filter,client:_}))),"sql"===o){const s=u(e,{pattern:t,allowEmpty:!0});if(!s.sql)return null;if(t=`${s.sql} ${E.filter||""} ${f?" order by "+f:""} ${l?"":" limit "+Number(p)+" OFFSET "+(Math.max(Number(d),1)-1)*Number(p)};SELECT FOUND_ROWS() AS total;`,R=R.concat(s.params||[],E.params),r){const s=u(e,{pattern:r,allowEmpty:!0});if(!s.sql)return null;t+=function(e,t){return e.indexOf("#APPENDSEARCH#")>=0?e.replace("#APPENDSEARCH#",t):e+" "+t}(s.sql,E.filter||""),R=R.concat(s.params||[],E.params)}}return{sql:t,fields:a,params:R,footers:m,page:d,hascounter:!!r}}},getDetailInfo:(e,t)=>{if(t){const r=s.getConfig(t);if(r&&r.detail){e.dataConfig=r;const{primary:t,field:s,primaryIsAutoIncrease:o}=r.detail;return{primary:t,fields:s,autoincrease:o}}}return null}}}var L,v={exports:{}};function B(){return L||(L=1,function(e){const t=q();class s{constructor({successed:e=!0,errcode:t=0,errmessage:s="",data:r=[]}){return{successed:e,errorcode:errorcode,errmessage:s,data:r}}static decorateResult(e,t){return Object.keys(t).forEach(s=>{e[s]=t[s]}),e}}s.DB_CONNECTED_FAILED={successed:!1,errmessage:"DB_CONNECTED_FAILED",errorcode:t.DATABASE_ERROR.DATABASE_CONNECTED_ERROR},s.DB_EXECUTE_FAILED={successed:!1,errorcode:t.DATABASE_ERROR.DATABASE_EXECUTE_ERROR},s.DB_NO_EFFECTIVE={successed:!1,errmessage:"DB_NO_EFFECTIVE",errorcode:t.DATABASE_ERROR.NO_RECORD_EFFECTED},s.DB_NO_RECORD_FOUND={successed:!1,errmessage:"DB_NO_RECORD_FOUND",errorcode:t.DATABASE_ERROR.NO_RECORD_FOUND},s.SUCCESS_RESULT={successed:!0,errorcode:0},s.RETURN_TO_INDEX={successed:!1,errorcode:t.COMMON_ERROR.VISIT_TO_INDEX},s.TOKEN_IS_EXPIRED={successed:!1,errmessage:"TOKEN_IS_EXPIRED",errorcode:t.COMMON_ERROR.TOKEN_EXPIRED,total:0,rows:[]},s.TOKEN_IS_INVALID={successed:!1,errmessage:"TOKEN_IS_INVALID",errorcode:t.COMMON_ERROR.TOKEN_IS_INVALID,total:0,rows:[]},s.TOKEN_IS_MISSING={successed:!1,errmessage:"TOKEN_IS_MISSING",errorcode:t.COMMON_ERROR.TOKEN_IS_MISSING,total:0,rows:[]},s.UNAUTHORIZATION_RESULT={successed:!1,errmessage:"UNAUTHORIZATION_RESULT",errorcode:t.COMMON_ERROR.UNAUTHORIZATION_ERROR,total:0,rows:[]},s.NO_ACCESS_RIGHT_RESULT={successed:!1,errmessage:"NO_ACCESS_RIGHT_RESULT",errorcode:t.COMMON_ERROR.NO_ACCESS_RIGHT,total:0,rows:[]},s.API_PARAMETERS_ERROR_RESULT={successed:!1,errmessage:"API_PARAMETERS_ERROR_RESULT",errorcode:t.COMMON_ERROR.API_PARAMETERS_ERROR,total:0,rows:[]},s.VERIFY_CODE_ERROR={successed:!1,errmessage:"VERIFY_CODE_ERROR",errorcode:t.COMMON_ERROR.VERIFY_CODE_ERROR,total:0,rows:[]},e.exports=s}(v)),v.exports}var j,P,F,k,$,V={exports:{}},K={};function H(){if(F)return P;F=1;const e=i,t=B(),{createDatabasePool:s}=function(){if(j)return K;j=1;const e=i,t=h().getCurrentApp();let s={};return K.createDatabasePool=r=>{if(null!=s[r])return s[r];const o=e.createPool(t.getConnection(r||"dev"));return s[r]=o,o},K}(),r=Symbol("executeSqlWithConnection");return P=class{constructor(e){this.pool=s(e)}escape(t){return e.escape(t)}escapeId(t){return e.escapeId(t)}logError(e,t,s=null){!0!==this.ingoreErrorLog&&this.actionLogger&&"function"==typeof this.actionLogger.logError&&(e||(e=this.constructor.name),this.actionLogger.logError({scene:e,error:t,user:s}))}async existedSqlData(e,t,s,r=!0){let o=await this.executeSql(e,t,s,r);return o.successed?o.rows&&0!=o.rows.length?{successed:!0,existed:!0,...o.rows[0]}:{successed:!0,existed:!1}:{successed:!1}}async getComputedRowValue(e,t,s,r=!0){let o=await this.executeSql(e,t,s,r);return o.successed&&0!=o.rows.length?{successed:!0,...o.rows[0]}:{successed:!1,errcode:-1,errmsg:"没有任何记录"}}getConnection(){return new Promise(e=>{if(!this.pool)return e(null);this.pool.getConnection(function(t,s){return e(t?null:s)})})}executeSql(e,s,o,n=!0){return o?this[r](e,s,o,n):new Promise((o,i)=>{if(!this.pool)return o(t.DB_CONNECTED_FAILED);this.pool.getConnection(async(i,a)=>{if(i)return o(t.DB_CONNECTED_FAILED);let l=await this[r](e,s,a,n);return o(l)})})}[r](e,s,r,o=!0){return r?new Promise(n=>r.query(e,s,(s,i)=>(o&&r.release(),s?(console.log("数据库操作错误",s,e),this.logError(null,"数据库操作错误:"+s+e),n(Object.assign(t.DB_EXECUTE_FAILED,{errmessage:"数据库操作错误"}))):n({successed:!0,rows:i})))):Promise.resolve(t.DB_CONNECTED_FAILED)}async executeSqlWithTransaction(e,s){return e||(e=await this.getConnection()),e?new Promise(r=>{e.beginTransaction(async o=>{if(o)return r({successed:!1,errcode:-1,errmessage:"【事务启动错误】"+o.message});let n={successed:!0};s&&"function"==typeof s&&(n=await s(e)),n.successed?e.commit(s=>s?(console.log("事务提交失败 :",s),r(Object.assign(t.DB_EXECUTE_FAILED,{errmessage:s.message}))):(e.release(),r(n))):e.rollback(()=>(e.release(),r(Object.assign(t.DB_EXECUTE_FAILED,{errmessage:"撤回操作"}))))})}):Promise.resolve({successed:!1})}}}function Y(){return k||(k=1,function(e){const t=H(),s=o;e.exports=class extends t{constructor(e){super(e&&e.database||"dev"),e&&(e.forcefilter=e.forcefilter||"",this.tableoption=e)}get hasPermissionControl(){return!!this.tableoption&&(this.tableoption.permission&&!isNaN(this.tableoption.permissiondatatype))}get permissionSql(){return this.hasPermissionControl?(this.tableoption.permissiondatatype,this.tableoption.primaryKey,"\n if (ifnull(vp.data_department, '') = '', ' and 1 = 1 ', ' and find_in_set('@user.department@',vp.data_department)')\n if (ifnull(vp.data_role, '') = '', ' and 1 = 1 ', ' and find_in_set('@user.role@',vp.data_role)')\n if (ifnull(vp.data_department, '') = '', ' and 1 = 1 ', ' and find_in_set('@user.id @',vp.data_user)')\n "):""}getBusiness(){return this.tableoption?this.tableoption.business:null}async loadData(e,t){return this.executeSql(e,t)}getByIdSql(){return`select * from ${this.tableoption.tableName} where ${this.tableoption.primaryKey}=? ${this.tableoption.forcefilter}`}updateSql(e){return`update ${this.tableoption.tableName} set ? where ${this.tableoption.primaryKey}=? ${this.tableoption.forcefilter}`}insertSql(){return`insert into ${this.tableoption.tableName} set ?`}deleteSql(){if(this.tableoption.logicDelete){let e=`update ${this.tableoption.tableName} set #DELETEBY# #DELETEDATE# ${this.tableoption.logicDeleteField||"rec_isdeleted"} =1 where ${this.tableoption.primaryKey} =? ${this.tableoption.forcefilter}`;return e=e.replace("#DELETEBY#",this.tableoption.logDeleteBy?`${this.tableoption.logDeleteBy}=?,`:""),e=e.replace("#DELETEDATE#",this.tableoption.logDeleteDate?`${this.tableoption.logDeleteDate}=now(),`:""),e}return`delete from ${this.tableoption.tableName} where ${this.tableoption.primaryKey} =? ${this.tableoption.forcefilter}`}BatchSql(){return`update ${this.tableoption.tableName} set ? where find_in_set(${this.tableoption.primaryKey},?) ${this.tableoption.forcefilter}`}async getBykey(e,t){return this.executeSql(e,t)}async create(e,t){return this.executeSql(e,t)}async update(e,t,s){return this.executeSql(e,[t,s])}async delete(e,t,s){return(t+"").trim().split(",").map(e=>"'"+e+"'"),this.tableoption.logicDelete&&this.tableoption.logDeleteBy?this.executeSql(e,[s,t]):this.executeSql(e,t)}async getDataPermissionSetting(e,t){if(!this.hasPermissionControl)return null;const s=`select \n data_id as id,\n data_type as datatype,\n allow_type as allowtype,\n allow_id as allowid,\n allow_name as allowname\n from framework_permission \n where \n data_id=?\n and data_type=? \n ${t}\n order by allow_type,allow_id\n `;return this.executeSql(s,[e,this.tableoption.permissiondatatype]).then(t=>{let s={successed:!0,managepermission:{},consumepermission:{datatype:this.tableoption.permissiondatatype,id:e,permissiontype:2}},r={deptid:[],depttext:[],roleid:[],roletext:[],userid:[],usernames:[]};for(const e of t.rows)switch(e.allowtype){case 1:r.deptid.push(e.allowid),r.depttext.push(e.allowname);break;case 2:r.roleid.push(e.allowid),r.roletext.push(e.allowname);break;case 4:r.userid.push(e.allowid),r.usernames.push(e.allowname)}return s.consumepermission.department=r.deptid.join(","),s.consumepermission.departmenttext=r.depttext.join(","),s.consumepermission.role=r.roleid.join(","),s.consumepermission.roletext=r.roletext.join(","),s.consumepermission.user=r.userid.join(","),s.consumepermission.usertext=r.usernames.join(","),s})}async saveDataPermissionSetting(e,t){if(!this.hasPermissionControl||!t)return Promise.resolve({successed:!0});let s="delete from framework_permission where data_id=? and data_type=?;",r=[];if(t.consumepermission){const s=t.consumepermission,o=s.department?s.department.split(","):[];for(const t of o)r.push([e,this.tableoption.permissiondatatype,1,t]);const n=s.role?s.role.split(","):[];for(const t of n)r.push([e,this.tableoption.permissiondatatype,2,t]);const i=s.user?s.user.split(","):[];for(const t of i)r.push([e,this.tableoption.permissiondatatype,4,t])}let o=[e,this.tableoption.permissiondatatype];return r.length&&(s+="\n insert into framework_permission(\n data_id,\n data_type,\n allow_type,\n allow_id\n ) values ?;\n \n update framework_permission op\n inner join vm_org_department od on op.allow_id=od.department_id\n set op.allow_name = od.department_name,\n op.allow_path = od.parent_path\n where data_id=? and data_type=? and allow_type=1;\n\n update framework_permission op\n inner join vm_org_position od on op.allow_id=od.position_id\n set op.allow_name = od.position_namecn\n where data_id=? and data_type=? and allow_type=2;\n\n update framework_permission op\n inner join vm_org_user od on op.allow_id=od.user_id\n set op.allow_name = od.user_name\n where data_id=? and data_type=? and allow_type=4;\n ",o.push(r,e,this.tableoption.permissiondatatype,e,this.tableoption.permissiondatatype,e,this.tableoption.permissiondatatype)),this.executeSql(s,o)}async batchUpdate(e,t,r,o){return this.tableoption.logicDelete&&this.tableoption.logDeleteBy&&null!=t[this.tableoption.logicDeleteField||"rec_isdeleted"]&&(t[this.tableoption.logDeleteBy]=o,this.tableoption.logDeleteDate&&(t[this.tableoption.logDeleteDate]=s().format("YYYY-MM-DD HH:mm:ss"))),this.executeSql(e,[t,r]).then(e=>({successed:!0,count:e.rows.affectedRows}))}}}(V)),V.exports}function X(){return $||($=1,function(e){const t=s,{Data2View:r,View2Data:o}=function(){if(y)return R;y=1;const{parseKeyValue:e,formatValue:t,validatorParamsType:s}=b();return R={Data2View:(e,s)=>{if(!e)return{successed:!0,data:null};if(!s||0==s.length)return{successed:!0,data:e};let r=[];for(const o of e){let e={};for(const r of s){if("backonly"==r.direction)continue;let s=o[r.name];!s&&r.nullValue&&(s=r.nullValue),r.format&&(s=t(s,r.format)),e[r.mapping||r.name]=s}r.push(e)}return{successed:!0,data:r}},View2Data:(t,r,o)=>{let n={},i={};if(Array.isArray(r))for(const a of r){if("frontonly"==a.direction)continue;if(a.action&&a.action.indexOf(o)<0)continue;let r=a.mapping||a.name,l=t.body[r];if(void 0!==l||("update"!=o||a.required)&&("create"!=o||a.required||a.default||a.nullValue)){if("string"==typeof l&&(a.trim&&1!=a.trim||l.trim(),a.maxlength&&l.length>a.maxlength))return{successed:!1,errcode:6,errmsg:"输入的长度超出,最大允许"+a.maxlength,name:a.mapping};if(l||(l=a.nullValue?e(t,a.nullValue):null),!l&&a.default&&(l=a.default),!0===a.required&&!l)return{successed:!1,errcode:5,errmsg:"请填写必填字段内容",name:r};if(a.type&&l&&!s(l,a.type))return{successed:!1,errcode:4,errmsg:`提交的值与要求的类型不匹配:(${r},${a.type})`,name:r};if(a.model){let e=i[a.model]||{};e[a.name]=l,i[a.model]=e}else n[a.name]=l}}else n=t.body;return t.modellist=i,{successed:!0,data:n}}}}(),n=S(),i=q(),{getListInfo:a,getDetailInfo:l,parseTagInSql:c}=M(),u=B(),d=Y(),p=n.getInstance();e.exports=class{constructor(e,s){this.app=e,this._redisHelper=this.app.redis,this.logger=this.app.logger,this.actionLogger=this.app.actionLogger,this._daoModel=s||new d,this._daoModel.actionLogger=this.actionLogger,this._daoModel.logger=e.logger,this._router=t.Router(),this.initializeRouter(this)}get router(){return this._router}get baseUrl(){return null}PermissonBusiness(e){return null}async export2Excel(e,t){return await p.recordset2ExcelFile(e,t,this.beforeExportExcel)}async export2MutlisheetExcel(e){if(!Array.isArray(e)||0==e.length)return{successed:!1};return await p.recordset2MutlisheetExcelFile(e,this.beforeExportExcel)}async writeExcel(e,t){return await p.writeExcel(e,t)}logUserAction(e,t,s,r=0,o=null){this.actionLogger&&t&&s&&this.actionLogger.log(e,t,s,r,o)}createCRUDRoute(e,t,s,r){let o=this;o.router[e.method](t,r||((e,t,s)=>s()),async(r,n)=>{let i,a=await o.beforeCRUD(e,r,n);return a.successed?(i="delete"===e.method?await o.delete(r,r.params.id):await o[e.func](r,s),i=await o.afterCRUD(i,e,s,t,r,n),n.json(i)):n.json(a)})}initializeCRUDRouter(e,t,s="SCRUD",r){if(!e||!t)return;let o=e.endsWith("/")?`${e}:id`:`${e}/:id`;s.indexOf("C")>=0&&this.createCRUDRoute(i.CRUDAction.Create,e,t,r),s.indexOf("S")>=0&&this.createCRUDRoute(i.CRUDAction.Single,o,t,r),s.indexOf("R")>=0&&this.createCRUDRoute(i.CRUDAction.Retrieve,e,t,r),s.indexOf("U")>=0&&this.createCRUDRoute(i.CRUDAction.Update,o,t,r),s.indexOf("D")>=0&&this.createCRUDRoute(i.CRUDAction.Delete,o,t,r)}async beforeCRUD(e,t,s){return{successed:!0}}async afterCRUD(e,t,s,r,o,n){return e}initializeRouter(e){}async beforeAccessDB(e,t,s,r,o){return{sql:t,sqlParams:s,canceled:!1}}beforeExportExcel(e){return e}async batchUpdate(e,t,s){if(s||(s=e.params.id),!s)return{successed:!1,errcode:-2,errmsg:"缺失批量操作的id"};let r=c(e,this._daoModel.BatchSql()),o=await this._daoModel.batchUpdate(r,t,s,e.user?.id);return this.logUserAction(e,this._daoModel.getBusiness(),6,o.successed?0:-1),o}async getListData(e,t,s=0){this.logger&&this.logger.trace("准备获取dataconfig文件中对应的 %s list数据",t);const o=a(e,t,s,this._daoModel);if(!o)return{successed:!1,errcode:-10,errmsg:`缺失${t}对应的查询语句`};let n=await this.beforeAccessDB(e,o.sql,o.params,"list",this);if(!0===n.canceled)return{successed:!1,errorcode:1,errmsg:"操作取消"};let i=await this._daoModel.loadData(n.sql,n.sqlParams);if(!i.successed)return"true"===e.query.exportexcel&&this.logUserAction(e,this._daoModel.getBusiness(),5,-1),i;if(i.rows){let s=r(i.rows[0],o.fields),n={successed:!0,page:o.page,rows:s.data};if(o.hascounter){let e=r(i.rows[2],o.footers);n.footer=e.data}return n.total=await this.getListRecordCount(i),"true"===e.query.exportexcel&&(n=await this.export2Excel(n.rows,e.query.excelkey||t),this.logUserAction(e,this._daoModel.getBusiness(),5,0)),n}return{successed:!1,errcode:-1,total:0,rows:[]}}async getListRecordCount(e){return e.rows[1][0].total}async getDataById(e,t,s,o){this.logger&&this.logger.trace("准备获取dataconfig文件中对应的 %s 详细数据",t);const n=l(e,t);if(!n)return{successed:!1,errcode:-10,errmsg:`缺失${t}对应的详情配置`};let i=await this.beforeAccessDB(e,s||this._daoModel.getByIdSql(),o||e.params.id,"detail",this);if(!0===i.canceled)return{successed:!1,errorcode:1,errormessage:"操作已取消"};let a=c(e,i.sql),d=await this._daoModel.getBykey(a,i.sqlParams);if(!d.successed)return d;if(d.rows&&1==d.rows.length){let t=r(d.rows,n.fields);if(this._daoModel.hasPermissionControl){const s=await this._daoModel.getDataPermissionSetting(e.params.id,this.PermissonBusiness(e));s.successed&&(t.data[0].managepermission=s.managepermission,t.data[0].consumepermission=s.consumepermission)}return{successed:!0,rows:t.data[0],id:e.params.id}}return u.DB_NO_RECORD_FOUND}async create(e,t,s){this.logger&&this.logger.trace("准备根据dataconfig文件中对应的 %s 配置插入数据",t);let r,n=e.query.Mapping??!0,i={successed:!0,data:e.body};if(1==n){if(r=l(e,t),!r)return{successed:!1,errcode:-10,errmsg:`缺失${t}对应的详情配置`};if(i=o(e,r.fields,"create"),!i.successed)return i}let a=await this.beforeAccessDB(e,s||this._daoModel.insertSql(),i.data,"create",this);if(a.canceled)return{successed:!1,errorcode:1,errormessage:"操作取消"};this.logger&&this.logger.trace("插入数据准备 : ",a);let c,u=await this._daoModel.create(a.sql,a.sqlParams,e);if(!u.successed)return this.logUserAction(e,this._daoModel.getBusiness(),1,-1),u;if(n&&r.primary&&(!0===r.autoincrease?c=u.rows.insertId:("string"==typeof r.primary&&(c=a.sqlParams[r.primary]),"object"==typeof r.primary&&(c=r.primary.map(e=>a.sqlParams[e])))),this._daoModel.hasPermissionControl){let t={};e.body.managepermission?t.managepermission=JSON.parse(e.body.managepermission):t.managepermission={},e.body.consumepermission?t.consumepermission=JSON.parse(e.body.consumepermission):t.consumepermission={},this._daoModel.saveDataPermissionSetting(c,t)}return this.logUserAction(e,this._daoModel.getBusiness(),1,0),{successed:!0,data:i.data,id:c}}async update(e,t,s,r){this.logger&&this.logger.trace("准备根据dataconfig文件中对应的 %s 配置修改数据",t),null==r&&(r=e.params.id);let n,i=e.query.Mapping??!0,a={successed:!0,data:e.body};if(1==i){if(n=l(e,t),!n)return{successed:!1,errcode:-10,errmsg:`缺失${t}对应的详情配置`};a=o(e,n.fields,"update")}let d=await this.beforeAccessDB(e,s||this._daoModel.updateSql(),a.data,"update",this);if(d.canceled)return{successed:!1,errorcode:1,errormessage:"操作取消"};this.logger&&this.logger.trace("修改数据准备 : ",d);let p=c(e,d.sql),f=await this._daoModel.update(p,d.sqlParams,r);if(!f.successed)return this.logUserAction(e,this._daoModel.getBusiness(),3,-1),f;if(1==f.rows.affectedRows){if(this._daoModel.hasPermissionControl){let t={};e.body.managepermission?t.managepermission=JSON.parse(e.body.managepermission):t.managepermission={},e.body.consumepermission?t.consumepermission=JSON.parse(e.body.consumepermission):t.consumepermission={},this._daoModel.saveDataPermissionSetting(r,t)}return this.logUserAction(e,this._daoModel.getBusiness(),3,0),{successed:!0,data:a.data,id:r}}return u.DB_NO_EFFECTIVE}async delete(e,t,s){this.logger&&this.logger.trace("准备删除数据",t);let r=await this.beforeAccessDB(e,s||this._daoModel.deleteSql(t),t,"delete",this);if(r.canceled)return{successed:!1,errorcode:1,errormessage:"操作取消"};let o=c(e,r.sql),n=await this._daoModel.delete(o,r.sqlParams,e.user?.id);return n.successed?(this.logUserAction(e,this._daoModel.getBusiness(),2,0),{successed:!0,id:t,count:n.rows.affectedRows}):(this.logUserAction(e,this._daoModel.getBusiness(),2,-1),n)}}}(w)),w.exports}var G,W,z={exports:{}};var J=a(W?u.exports:(W=1,u.exports={doomiwork:g(),controller:X(),model:Y(),appsetting:h(),actionresult:B(),excelutility:S(),tokenHelper:(G||(G=1,function(e){class t{constructor(e){this.cache=e}setToken(e,t,s){return this.cache.set(e,t,s)}async getToken(e,t=!0){let s=await this.cache.get(e);return s&&t?JSON.parse(s):s}async tokenIsValid(e){return null!=await this.getToken(e,!1)}deleteToken(e){this.cache.delete(e)}extendToken(e,t){return this.cache.expire(e,t)}}e.exports.TokenHelper=e=>new t(e)}(z)),z.exports),constants:q()}));export{J as default};//# sourceMappingURL=index.esm.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.esm.js","sources":["../configuration/appsetting.js","../core/doomiwork.js","../configuration/routerconfig.js","../utilities/keywordparse.js","../utilities/excelutility.js","../core/enumconst.js","../configuration/dataconfig.js","../utilities/requestparser.js","../core/actionresult.js","../core/database/mysqlbase.js","../core/database/poolmanager.js","../core/database/daoBase.js","../core/controller.js","../utilities/transferutility.js","../index.js?commonjs-entry","../index.js","../utilities/tokenutility.js"],"sourcesContent":["const path = require('path');\nconst fs = require('fs');\nclass appsetting{\n constructor(){\n let config = process.env.CONFIGFILE || 'configuration.json';\n \n let configfile = path.join(process.cwd(), config);\n if (!fs.existsSync(configfile))throw new Error('missing app configuration file')\n this.settingjson = require(configfile);\n }\n /**\n * 单例模式\n * @param {*} config \n */\n static getCurrentApp(){\n if (!appsetting.app) appsetting.app = new appsetting();\n return appsetting.app;\n }\n /**\n * 获取到框架配置文件中的设置节点\n * @param {*} settingKey \n * @param {*} defaultValue \n */\n getSetting (settingKey,defaultValue) {\n if (!this.settingjson || !this.settingjson.appsetting) return defaultValue;\n const item= this.settingjson.appsetting[settingKey];\n return item??defaultValue;\n }\n getSection(sectionName){\n return this.settingjson[sectionName];\n }\n /*\n * 获取配置文件中的数据库连接串\n */\n getConnection (connName) {\n return this.settingjson.connections[connName];\n };\n}\nexports=module.exports = appsetting;","/*\n Doomisoft框架入口类\n 自动加载配置与routerConfig中的路由配置\n*/\nconst { loadController } = require('../configuration/routerconfig')\nconst config = require('../configuration/appsetting').getCurrentApp();\nconst fs = require('fs');\nconst path = require('path')\nclass Doomiwork { \n static startWork(application,option={}) {\n application.config = config;\n ///启动redis进行缓存\n ////为每个controller注入同一个redis实例\n if (config.getSetting(\"redis\", false) === true && option.redis){\n application.redis = option.redis;// redisHelper.getInstance();\n }\n ////记录用户行为的日志记录器\n // const logHandler = config.getSetting(\"logaction\", null)\n // if (logHandler){\n // let actionLogger = path.join(startupRoot, logHandler);\n // if (actionLogger && fs.existsSync(actionLogger)) {\n // const logInstance = require(actionLogger);\n // application.actionLogger = new logInstance();\n // }\n // }\n ///用户操作日志记录\n if(config.getSetting(\"logaction\", false)===true && option.logaction) application.actionLogger = option.logaction;\n ///日志记录器\n if (config.getSetting(\"logger\", false) === true && option.logger) application.logger = option.logger;// redisHelper.getInstance();\n //application.logger = logHelper.getInstance().getLogger(\"framework\");\n /**全局所有请求拦截器 */\n application.use('/',(req,res,next)=>{\n req.user = req.headers;\n return next();\n });\n /**\n * 注册监控路由\n */\n if (!(option.monitor===false)) this.registerMonitorRouter(application)\n /** 加载所有的控制器 */\n if (!option.routes){\n const roterfile = path.join(process.cwd(), 'routerconfig.json');\n ///将配置中的所有需要加载的controller文件都加载出来\n if (fs.existsSync(roterfile)){\n option.routes = require(roterfile)\n }\n }\n loadController(application, option.routes)\n Doomiwork.app = application;\n }\n\n static registerMonitorRouter(app){\n if (!app) return;\n app.get('/_doomiwork_/version', (_req, res) => {\n const packjson = path.join(process.cwd(), 'package.json');\n if (fs.existsSync(packjson)){\n const { name, version } = require(packjson);\n return res.json({ successed:true, name, version });\n }\n return res.json({successed:false,message:\"not found package.json\"})\n });\n app.post('/_doomiwork_/upload', async (req, res) => {\n const { question, content, __doomiwork__token__ } = req.body;\n if (__doomiwork__token__ !== 'Spy@20060516') return res.status(404).send(\"404 Not Found\");\n if (!question || question.length < 4) return res.json(FuncResult.failed(-1, 'question is required and question must be more than 4 characters'));\n const filepath = path.resolve(question);\n if (!fs.existsSync(filepath)) return res.status(500).send(\"can not found question\");\n fs.writeFileSync(filepath, content, { encoding: 'utf8', flag: 'w' })\n return res.send('Ok');\n });\n }\n /**\n * 注册url请求拦截函数\n * @param {*} baseUrl \n * @param {*} intrupFilter \n */\n static registerUrlInterceptor(app,baseUrl,intrupFilter){\n if (intrupFilter){\n app.use(baseUrl,intrupFilter);\n }\n }\n /**\n * 注册一组同组的请求路径的拦截器\n * @param {*} baseUrl \n * @param {*} intrupFilter \n */\n static registerGroupInterceptor(app,groupName,intrupFilter){\n if (groupName && intrupFilter){\n if (!app.Interceptor) app.Interceptor = {};\n app.Interceptor[groupName] = intrupFilter;\n }\n }\n}\nexports = module.exports = Doomiwork;","/*\n* dataconfig配置文件的处理模块\n*/\nconst fs = require('fs');\nconst path = require('path')\n////扫描Controller文件夹时需要排除的目录\nconst IGNORE_FOLDER = [\"script\", \"scripts\", \"js\", \"image\", \"data\", \"video\", \"images\", \"style\", \"css\", \"app_themes\"];\n/**\n * 加载控制器目录下的所有JS文件形成路由\n * @param {*} result \n * @param {*} routeGroup \n */\nconst loadFolderFiles4Router = (result, startPath, routeGroup)=> {\n const exceptFile = routeGroup.exceptfile;\n const exceptfolder = routeGroup.exceptfolder;\n const scanFolder = path.join(startPath, routeGroup.folder);\n getFolderControllerFiles(result, scanFolder, exceptFile, exceptfolder);\n}\n/**\n * 遍历加载整个文件夹下面的所有文件形成路由\n * @param {*} result \n * @param {*} startPath \n * @param {*} execfiles \n * @param {*} execfolder \n */\nconst getFolderControllerFiles=(result, startPath, execfiles, execfolder) =>{\n const files = fs.readdirSync(startPath);\n for (const val of files) {\n const fPath = path.join(startPath, val);\n const stats = fs.statSync(fPath);\n ////是个目录\n if (stats.isDirectory()) {\n if (execfolder == null || execfolder.indexOf(fileName) < 0)\n findFolderFiles(result, fPath, fPath, execfiles, execfolder);\n }\n ///是个文件\n else if (stats.isFile()) {\n let fileExtion = path.extname(fPath).toLowerCase();\n if (fileExtion !== \".js\") continue;\n let fileName = path.basename(fPath);\n fileName = fileName.substr(0, fileName.length - fileExtion.length);\n if (!execfiles || execfiles.indexOf(fileName) < 0) result.push(fPath);\n }\n }\n}\n\n/**\n * 遍历加载整个文件夹下面的所有文件形成路由\n * @param {*} result \n * @param {*} baseFolder \n * @param {*} startPath \n * @param {*} execfiles \n * @param {*} execfolder \n */\nconst findFolderFiles = (result, baseFolder, startPath, execfiles, execfolder)=> {\n let files = fs.readdirSync(startPath);\n // files.forEach((val) => {\n for (const val of files) {\n let fPath = path.join(startPath, val), stats = fs.statSync(fPath), fileName = fPath.substr(baseFolder.length + 1);\n if (stats.isDirectory()) {\n ///排除基本的忽略目录\n if (IGNORE_FOLDER.includes(fileName.toLowerCase())) continue;\n if (execfolder == null || execfolder.indexOf(fileName) < 0)\n findFolderFiles(result, baseFolder, fPath, execfiles, execfolder);\n }\n if (stats.isFile()) {\n let fileExtion = path.extname(fPath).toLowerCase();\n if (fileExtion != \".html\") continue;\n let fileName = fPath.substr(baseFolder.length + 1);\n fileName = fileName.substr(0, fileName.length - fileExtion.length);\n if (execfiles == null || execfiles.indexOf(fileName) < 0) result.push(fileName);\n }\n }\n}\n/**\n * 动态加载\n * @param {*} app \n * @param {*} routes \n * @returns \n */\nconst loadController = (app, routes) => {\n ///定位置项目启动目录,准备遍历所有controller目录\n if (!Array.isArray(routes) || !routes.length) return;\n let startupRoot = process.cwd();\n //let routes = routelist?routelist:this.routerconfig ;\n for (const element of routes) {\n //if (!element.routers || element.routers.length == 0) return;\n ///路由被禁用,则略过\n if (element.disabled) continue;\n ///包含文件\n if (element.include) {\n let includeRouteJson = path.join(startupRoot, element.include);\n console.log('includeRouteJson', includeRouteJson)\n ///如果包含文件存在,则加载这个文件里面的路由\n if (fs.existsSync(includeRouteJson)) {\n loadController(app, require(includeRouteJson));\n }\n }\n else {\n let modules = [];\n let { baseUrl, groupName } = element.routefolder ? element.routefolder : element;\n if (groupName && app.Interceptor[groupName]) app.use(baseUrl, app.Interceptor[groupName])\n if (element.routefolder) {\n if (element.routefolder.folder) loadFolderFiles4Router(modules, startupRoot, element.routefolder);\n }\n ////单文件\n else {\n if (fs.existsSync(path.join(startupRoot, element.controller)))\n modules.push(path.join(startupRoot, element.controller));\n }\n ////单个文件的加载\n if (modules.length > 0) {\n for (const modulePath of modules) {\n //if (app.logger) app.logger.trace('initlize controller [%s] for baseUrl [%s]', modulePath, baseUrl);\n // console.log('initlize controller [%s] for baseUrl [%s]', modulePath, baseUrl);\n const controllModule = require(modulePath);\n const controller = new controllModule(app);\n app.use(baseUrl, controller.router);\n }\n\n }\n }\n }\n}\n// class routerconfig {\n// constructor(routerfile) {\n// ///路由的配置文件\n// let configfile = path.join(process.cwd(), routerfile || 'routerconfig.json');\n// if (fs.existsSync(configfile)) {\n// this.routerconfig = require(configfile);\n// } else {\n// this.routerconfig = [];\n// }\n// }\n// /**\n// * 单例模式\n// * @param {*} config \n// */\n// static getInstance() {\n// if (!routerconfig.setting) routerconfig.setting = new routerconfig();\n// return routerconfig.setting;\n// }\n/**\n * 加载应用下所有配置的controller文件\n * @param {*} controllerconfig \n * @param {*} providerCollection \n */\nmodule.exports = { loadController }\n\n// }\n// module.exports = routerconfig;\n","\n/**\n * 解析上下文中对应dataconfig文件中的一些变量解析\n */\n// const uuid = require('uuid'); \nconst {randomUUID} = require('crypto')\nconst moment = require('moment')\n/*\n* 从上下文 解析关键字\n* 或者已固定的方式解析关键字\n*/\nconst parseKeyValue=(req,str)=>{\n if (!str) return str||'';\n const strItems = str.split('.');\n if (strItems.length===1)\n {\n switch(str.toLowerCase()){\n case \"userid()\": \n if (req.user && req.user.id) return req.user.id;\n return randomUUID();\n case \"uuid()\": return randomUUID();\n case \"appid()\" : \n if (req.user && req.user.appid) return req.user.appid; \n return null;\n case \"orgid()\" : \n if (req.user && req.user.id) return req.user.orgnizations; \n return null;\n case \"now()\": return moment().format('YYYY-MM-DD HH:mm:ss');\n case \"null()\": return null;\n default: return (req.body && req.body[str])||(req.query && req.query[str])||'';\n }\n }\n else\n {\n let collection;\n if (strItems[0]==\"\" || strItems[1]==\"\") return str;\n switch(strItems[0].toLowerCase())\n {\n case \"query\" : collection = req.query; break;\n case \"form\": collection = req.body;break;\n case \"params\": collection = req.params; break;\n case \"value\": return strItems[1];\n case \"headers\": collection = req.headers; break; \n case \"user\": collection = req.user || {}; break; \n default: collection = req.body; break;\n }\n if (collection) return collection[strItems[1]] || '';\n return '';\n }\n}\n\n/**\n * 校验参数的类型\n * @param {*} value 数值\n * @param {*} dataType 校验的类型\n * @param {*} defaultValue 如果不满足,则返回默认的\n * @returns \n */\nconst validatorParamsType = (value, dataType, defaultValue = null, inscope=[])=> {\n if (!value || !dataType) return value;\n switch (dataType.toLowerCase()) {\n case 'guid': ///限制长度为36位的GUID\n if (value.length != 36 || value.split('-').length != 5) value= defaultValue;\n break;\n case 'number': ///限制为数字\n if (isNaN(value)) value= defaultValue;\n break;\n case 'date': ///限制为日期,格式输出为YYYY-MM-DD\n let date = Date.parse(value);\n if (isNaN(date)) return defaultValue;\n return moment(date).format('YYYY-MM-DD');\n case 'datetime': ///限制为包含时间的日期\n let datetime = Date.parse(value);\n if (isNaN(datetime)) return defaultValue;\n return datetime;\n case 'array': ///返回数组\n value= value.split(',');\n }\n ///检查值在不在范围内取值\n let inRange = true;\n if (inscope.length > 0 && value) {\n inRange = false;\n if (Array.isArray(value)) {\n for(const item of value){\n if (inscope.some(scope => scope.toLowerCase() === item.toLowerCase())){\n inRange = true;\n break;\n } \n }\n } else {\n inRange = inscope.some(scope => scope.toLowerCase() === value.toLowerCase())\n }\n }\n return inRange ? value : defaultValue;\n}\n\n/**\n * 将原始值format后输出\n * @param {*} value 123\n * @param {*} format ${value}\n * @returns \n */\nconst formatValue = (value, format)=> {\n if (!format) return value;\n return format.replace(/\\${value}/ig,value)\n // let formatItem = format.split('|');\n // let coll = {};\n // formatItem.forEach(item => {\n // if (item == '') return;\n // var itemValues = item.split(':');\n // if (itemValues.length != 2) return;\n // coll[itemValues[keyIndex]] = itemValues[1 - keyIndex];\n // })\n // //let jsonFormat =JSON.parse('{'+format+'}');\n // return coll[value];\n}\n\nmodule.exports = {\n parseKeyValue,\n validatorParamsType,\n formatValue\n}","const xlsx = require('node-xlsx');\nconst fs = require('fs');\nconst path = require('path');\nconst {randomUUID:uuid} = require('crypto');\nclass ExcelUtility {\n constructor() {\n this.exportFolder = path.join(process.cwd(), '/public/excel/');\n let configfile = path.join(process.cwd(), 'excelconfig.json');\n if (fs.existsSync(configfile))\n this.excelConfig = require(configfile);\n else\n this.excelConfig = {};\n }\n static getInstance() {\n if (!ExcelUtility.instance) ExcelUtility.instance = new ExcelUtility();\n return ExcelUtility.instance;\n }\n ///读取Excel的内容\n readExcel(fileName) {\n //读取文件内容\n const obj = xlsx.parse(fileName);//__dirname+'/test.xlsx');\n const excelObj = obj[0].data;\n console.log(excelObj);\n return excelObj;\n }\n ///写Excel文件\n createExcelBuffer(data, fileName, workSheetName) {\n var sheetName = 'sheet1';\n if (workSheetName == null) sheetName = workSheetName;\n var buffer = xlsx.build([{ name: 'sheet1', data: data }]);\n\n res.set({\n \"Content-type\": \"application/octet-stream\",\n \"Content-Disposition\": \"attachment;filename=\" + encodeURI(fileName)\n });\n fReadStream = fs.createReadStream(buffer);\n fReadStream.on(\"data\", (chunk) => res.write(chunk, \"binary\"));\n fReadStream.on(\"end\", () => {\n res.end();\n });\n }\n ///写Excel文件\n async writeExcel(data, workSheetName) {\n let sheetName = 'sheet1';\n if (workSheetName == null) sheetName = workSheetName;\n let randomFile = uuid() + '.xlsx';\n let fileName = path.resolve(this.exportFolder, randomFile);\n let _saveDir = path.dirname(fileName);\n ///创建本地文件夹\n if (!this.mkdirsSync(_saveDir)) return { success: false, errorcode: 1, errmessage: 'create folder failed!' };\n const buffer = xlsx.build([{ name: sheetName, data: data }]);\n return new Promise(reslove => {\n return fs.writeFile(fileName, buffer, (err) => {\n return reslove({ successed: !err, errmessage: err, fileName:randomFile })\n })\n })\n }\n ///导出记录集到Excel,写入\n ///dataRow :记录集\n ///exportConfig : 导出的映射配置,如没有则将dataRow直接导出\n ///workSheetName : 导出的Excel 文件 WorkSheet名\n async recordset2ExcelFile(dataRow, exportConfig, readyDataFunc) {\n let _instance = this;\n //var setting = exportConfig ? excelConfig[exportConfig] : null;\n let setting = exportConfig ? _instance.excelConfig[exportConfig] : null;\n let dataBuffer = [], worksheetName = \"sheet1\", fieldKey = [], titleRow = [];\n if (setting != null) {\n worksheetName = setting.worksheet ?? \"sheet1\"; //== null ? \"sheet1\" : setting.worksheet;\n ////第一行导出标题行\n setting.columns.forEach((field) => {\n var dataOption = { type: 'title', config: exportConfig, title: field.title, field: field.name };\n if (readyDataFunc != null && typeof (readyDataFunc) == \"function\")\n dataOption = readyDataFunc(dataOption)\n titleRow.push(dataOption.title);\n fieldKey.push(dataOption.field);\n });\n }\n else if (dataRow.length > 0) {\n var firstRow = dataRow[0];\n Object.keys(firstRow).forEach(key => {\n var dataOption = { type: 'title', config: null, title: key, field: key };\n if (readyDataFunc != null && typeof (readyDataFunc) == \"function\")\n dataOption = readyDataFunc(dataOption)\n titleRow.push(dataOption.title);\n fieldKey.push(dataOption.field);\n });\n }\n if (titleRow.length > 0) {\n dataBuffer.push(titleRow);\n dataRow.forEach((rowItem) => {\n var dataRow = [];\n fieldKey.forEach((field) => {\n var dataOption = { type: 'data', config: exportConfig, field: field, data: rowItem, value: rowItem[field] };\n if (readyDataFunc != null && typeof (readyDataFunc) == \"function\")\n dataOption = readyDataFunc(dataOption)\n dataRow.push(dataOption.value);\n });\n dataBuffer.push(dataRow);\n })\n }\n var result = await _instance.writeExcel(dataBuffer, worksheetName);\n return result;\n }\n\n ///写Excel文件\n async writeMutlisheetExcel(sheetinfo) {\n //let sheetName = 'sheet1';\n //if (workSheetName == null) sheetName = workSheetName;\n let randomFile = uuid() + '.xlsx';\n let fileName = path.resolve(this.exportFolder, randomFile);\n let _saveDir = path.dirname(fileName);\n ///创建本地文件夹\n if (!this.mkdirsSync(_saveDir)) return { success: false, errorcode: 1, errmessage: 'create folder failed!' };\n const buffer = xlsx.build(sheetinfo);// ([{ name: sheetName, data: data }]);\n return new Promise(reslove => {\n return fs.writeFile(fileName, buffer, (err) => {\n return reslove({ successed: !err, errmessage: err, fileName: randomFile })\n })\n })\n }\n /**\n * 导出记录集到Excel的多个worksheet中\n * @param {*} dataRow \n * @param {*} exportConfig \n * @param {*} readyDataFunc \n * @returns \n */\n async recordset2MutlisheetExcelFile(sheetsInfo, readyDataFunc) {\n let _instance = this;\n let sheetinfo = [];\n for (const { data: dataRow, mapping: exportConfig } of sheetsInfo){\n let setting = exportConfig ? _instance.excelConfig[exportConfig] : null;\n let dataBuffer = [], worksheetName = \"sheet1\", fieldKey = [], titleRow = [];\n if (setting != null) {\n worksheetName = setting.worksheet == null ? \"sheet1\" : setting.worksheet;\n ////第一行导出标题行\n setting.columns.forEach((field) => {\n var dataOption = { type: 'title', config: exportConfig, title: field.title, field: field.name };\n if (readyDataFunc != null && typeof (readyDataFunc) == \"function\")\n dataOption = readyDataFunc(dataOption)\n titleRow.push(dataOption.title);\n fieldKey.push(dataOption.field);\n });\n }\n else if (dataRow.length > 0) {\n var firstRow = dataRow[0];\n Object.keys(firstRow).forEach(key => {\n var dataOption = { type: 'title', config: null, title: key, field: key };\n if (readyDataFunc != null && typeof (readyDataFunc) == \"function\")\n dataOption = readyDataFunc(dataOption)\n titleRow.push(dataOption.title);\n fieldKey.push(dataOption.field);\n });\n }\n if (titleRow.length > 0) {\n dataBuffer.push(titleRow);\n dataRow.forEach((rowItem) => {\n var dataRow = [];\n fieldKey.forEach((field) => {\n var dataOption = { type: 'data', config: exportConfig, field: field, data: rowItem, value: rowItem[field] };\n if (readyDataFunc != null && typeof (readyDataFunc) == \"function\")\n dataOption = readyDataFunc(dataOption)\n dataRow.push(dataOption.value);\n });\n dataBuffer.push(dataRow);\n })\n }\n sheetinfo.push({ name: worksheetName, data: dataBuffer });\n }\n const result = await _instance.writeMutlisheetExcel(sheetinfo);\n return result;\n }\n\n /**\n * 递归创建多级目录\n * @param {*} dirpath \n * @param {*} mode \n * @returns \n */\n mkdirsSync(dirpath, mode) {\n if (!fs.existsSync(dirpath)) {\n let pathtmp;\n const splitPath = dirpath.split(path.sep);\n for (var nLoop = 0; nLoop < splitPath.length; nLoop++) {\n var dirname = splitPath[nLoop];\n if (dirname.length == 0) {\n pathtmp = \"/\";\n continue;\n }\n if (pathtmp)\n pathtmp = path.join(pathtmp, dirname);\n else\n pathtmp = dirname;\n if (!fs.existsSync(pathtmp)) {\n fs.mkdirSync(pathtmp, mode)\n }\n }\n }\n return true;\n }\n}\nexports = module.exports = ExcelUtility;","/*\n* 常用的API返回错误枚举\n*/\n///数据库级别的错误 : FROM 10001 ~ 10100\nmodule.exports.DATABASE_ERROR = {\n DATABASE_CONNECTED_ERROR: 10001,\n DATABASE_EXECUTE_ERROR: 10002,\n NO_RECORD_EFFECTED: 10003,\n NO_RECORD_FOUND: 10004\n}\n///通用错误 : From 9000~10000\nmodule.exports.COMMON_ERROR = {\n TRANSMIT_TO_VIEW_ERROR: 9000,\n TRANSMIT_TO_DATA_ERROR: 9001,\n\n\n VISIT_TO_INDEX: 9002, //访问跟域名,返回到首页\n API_PARAMETERS_ERROR: 9003, //API方法调用错误\n VERIFY_CODE_ERROR: 9004, //验证码错误\n /////权限操作类错误\n NO_ACCESS_RIGHT: 9100, //没有访问权限\n TOKEN_IS_MISSING: 9997,\n TOKEN_EXPIRED: 9998, //\n TOKEN_IS_INVALID: 9999, //密匙无效\n UNAUTHORIZATION_ERROR: 10000 //未认证\n}\n///用户登录错误码\nmodule.exports.LOGIN_ERROR = {\n SUCCESSED: 0,\n USER_NOT_FOUND: 1,\n USER_PASSWORD_ERROR: 2,\n SERIAL_CODE_ERROR: 3, ///校验码无效\n UNKNOW_ERROR: 4,\n DATABASE_ERROR: 100\n};\n///获取用户属性错误码\nmodule.exports.GET_USERINFO_ERROR = {\n SUCCESSED: 0,\n USER_NOT_FOUND: 1,\n UNKNOW_ERROR: 2,\n DATABASE_ERROR: 100\n};\n/**\n * CRUD操作所对应的web method以及框架对应的调用方法\n */\nmodule.exports.CRUDAction = {\n Create:{method:'post',name:'create',func:'create'},\n Retrieve:{method:'get',name:'list',func:'getListData'},\n Single:{method:'get',name:'single',func:'getDataById'},\n Update:{method:'put',name:'update',func:'update'},\n Delete:{method:'delete',name:'delete',func:'delete'}\n}","/*\n* dataconfig配置文件的处理模块\n*/\nconst fs = require('fs');\nconst path = require('path')\nclass dataConfig\n{\n constructor(){\n let configfile = path.join(process.cwd(),'dataconfig.json');\n let comcfgfile = path.join(process.cwd(),'simplecommon.json');\n ////检查dataconfig.json文件是否存在,优先加载dataconfig.json\n if (!fs.existsSync(configfile)){\n ///如果json文件不存在,则加载后缀为js的文件\n configfile = path.join(process.cwd(),'dataconfig.js');\n if (!fs.existsSync(configfile)) \n this.cache = {}; //throw new Error('missing app configuration file')\n else\n this.cache = require(configfile); \n }else\n this.cache = require(configfile); \n ////优先加载simplecommon.json文件\n if (fs.existsSync(comcfgfile)){\n this.commoncache = require(comcfgfile); \n }else{\n comcfgfile = path.join(process.cwd(),'simplecommon.js');\n if (fs.existsSync(comcfgfile))\n this.commoncache = require(comcfgfile); \n else\n this.commoncache = {};\n }\n \n }\n /*\n *根据名称获取到配置中的对应节\n */\n getConfig(itemName,cfgType=0) {\n return cfgType==0?this.getDataConfig(itemName):this.getCommonConfig(itemName);\n }\n\n /**\n * 单例模式\n * @param {*} config \n */\n static getCurrent(){\n if (!dataConfig.data) dataConfig.data = new dataConfig();\n return dataConfig.data;\n }\n\n getDataConfig(itemName) {\n return this.cache[itemName];\n }\n\n getCommonConfig(itemName) {\n return this.commoncache[itemName];\n }\n}\nmodule.exports = dataConfig;\n","const { parseKeyValue, validatorParamsType } = require('./keywordparse');\nconst dataconfig = require('../configuration/dataconfig').getCurrent();\nconst mysql = require('mysql');\nconst ORDER_STRING = ['asc', 'desc']\nconst FORBID_SQL_KEYWORD = /;|(--)|(\\bWHERE\\b)|(\\bCASE\\b)|(\\bWHEN\\b)|(\\bSLEEP\\b)|(\\bSHOW\\b)|(\\bCOUNT\\(\\b)|(\\bCREATE\\b)|(\\bCALL\\b)|(\\bBY\\b)|(\\bORDER\\b)|(\\bJOIN\\b)|(\\bUNION\\b)|(\\bFROM\\b)|(\\bSELECT\\b)|(\\bDROP\\b)|(\\bTRUNCATE\\b)|(\\bDELETE\\b)|(\\bUPDATE\\b)|(\\bINSERT\\b)|(\\bEXEC\\b)|(\\bEXECUTE\\b)/gi;\n\nfunction appendSearchCondition2Count(originSql, searchCondition) {\n ///如果包含了这个特定的字符,则替换\n if (originSql.indexOf('#APPENDSEARCH#') >= 0)\n return originSql.replace('#APPENDSEARCH#', searchCondition);\n return originSql + ' ' + searchCondition;\n}\n/**\n * 检查是否有Sql注入的风险\n * @param {*} sql \n */\nfunction checkSqlInjection(sql) {\n if (!sql) return sql;\n if (FORBID_SQL_KEYWORD.test(sql)) return '';\n return sql;\n}\n\nfunction isEmptyValue(value){\n if (value === undefined || value === null || value === '') return true;\n return false;\n}\n/*\n* 根据对应列表的配置(dataConfig.list.search),从请求上下文中获取用户进行搜索的参数信息\n*/\n\nconst getSearchCondition = (option) => {\n let paraCopy = option || {};\n if (!paraCopy.request || !paraCopy.refer) return { filter: '', params: [] };\n if (!paraCopy.valueFrom) paraCopy.valueFrom = \"all\";\n const request = paraCopy.request;\n let retSearch = [], params = [];\n paraCopy.refer.forEach(element => {\n const paramSql = parseTagForParameterize(request, element);\n if (paramSql.sql) {\n retSearch.push(paramSql.sql);\n params = params.concat(paramSql.params || []);\n }\n });\n return { filter: retSearch.join(''), params }\n //return retSearch.join('');\n}\n\n\n/**\n * 解析sql字符串中特殊的占位符\n * @param {*} req \n * @param {*} sql \n * @param {*} allowNull \n * @returns \n */\nconst parseTagInSql = (req, sql, allowNull = true) => {\n if (!sql) return '';\n ///定义正则准备查找sql中的特定关键字\n const matched = sql.match(/@.*?@/g);\n if (!matched || matched.length <= 0) return sql;\n let parseKeyWordIsNull = false;\n const charReg = /\\s+|:|=/gi\n matched.forEach(ele => {\n let matchValue = ele.substring(1, ele.length - 1);\n ///不允许特殊字符出现\n let notdo = matchValue.match(charReg);\n if (notdo && notdo.length > 0) return;\n\n let noQuoteProtect = matchValue[0] == '!';\n if (noQuoteProtect) matchValue = matchValue.substring(1);\n ///是否有格式要求\n let validformat = matchValue.split('|');\n matchValue = validformat[0];\n let keyValue = (parseKeyValue(req, matchValue) || '')+''; //utility.ifNull(keyParse.parseKeyValue(req, matchValue), '')+'';\n if (!keyValue) {\n parseKeyWordIsNull = true;\n } else if (typeof (keyValue) === 'string') {\n keyValue = noQuoteProtect ? checkSqlInjection(mysql.escape(keyValue)) : mysql.escape(keyValue)\n keyValue = keyValue.substring(1, keyValue.length - 1);\n ///验证参数的格式合法性\n if (keyValue && validformat.length > 1) keyValue = validatorParamsType(keyValue, validformat[1], validformat[2])\n if (!keyValue) {\n parseKeyWordIsNull = true;\n }\n ///没有引号保护下发现了sql注入,则用1=0不返回任何结果\n if (!keyValue && noQuoteProtect) keyValue = '1=0'\n } else { ////数组形式的参数,目前框架不支持,统一认为为sql注入攻击,全部忽略\n // console.log(`参数非法==>类型${typeof (keyValue)}:${matchValue} = ${keyValue}`)\n parseKeyWordIsNull = true;\n keyValue = ''\n }\n sql = sql.replace(ele, keyValue);\n });\n if (!allowNull && parseKeyWordIsNull) return '';\n return sql;\n}\n\n\n/**\n * 为列表查询定义参数化查询\n * @param {*} req \n * @param {*} sql \n * @param {*} allowNull \n * @param {*} isSearch \n * @returns \n */\nconst parseTagForParameterize = (req, filterSetting={}) => {\n ///type=parameter表示参数化方式查询\n ///type=joint 表示拼接sql语句查询\n ///scope=[] 表示需要解析的字段必须在此列表内容中\n /// split 进来的替换内容是否需要被split拆分成多个参数\n let {pattern:sql,type='parameter',inscope=[],allowEmpty=false,split=false,subitem,splitjoint='or',splitchar='|'} = filterSetting;\n if (!sql) return {sql:''};\n ///定义正则准备查找sql中的特定关键字\n const matched = sql.match(/@.*?@/g);\n let params = [];\n if (!matched || matched.length <= 0) return {sql};\n for(const ele of matched){\n let matchValue = ele.substring(1, ele.length - 1);\n ///检查是否有特殊的字符比如 % 等\n const specialRegex = /^[^a-zA-Z0-9]*(.*?)[^a-zA-Z0-9]*$/\n const matchContent = matchValue.match(specialRegex);\n matchValue = matchContent ? matchContent[1]:matchValue;\n if (!matchValue) return {sql:'',params:[]};\n ///是否有格式要求\n let validformat = matchValue.split('|');\n matchValue = validformat[0];\n \n let keyValue = parseKeyValue(req, matchValue)||''; //utility.ifNull(keyParse.parseKeyValue(req, matchValue), '')+'';\n if (keyValue && validformat.length > 1) keyValue = validatorParamsType(keyValue, validformat[1], validformat[2], inscope)\n ///如果解析不出这个KeyValue ,则认为当前这条SQL过滤无效\n if (isEmptyValue(keyValue) && !allowEmpty) return {sql:'',params:[]};\n // if (keyValue) {\n if(type.toLowerCase() === 'parameter'){\n /// 需要用|拆分成多个参数\n if(split && subitem){\n const multiParams = keyValue.split(splitchar),multiItems = [];\n for(const subitemValue of multiParams){\n multiItems.push(subitem);\n params.push(matchContent[0].replace(matchContent[1], subitemValue));\n }\n sql = sql.replace(ele, multiItems.join(' '+splitjoint+' '));\n }else{\n sql = sql.replace(ele, '?'); ///变成参数化查询\n if (Array.isArray(keyValue))\n params.push(keyValue)\n else\n params.push(matchContent[0].replace(matchContent[1], keyValue));// '%' + keyValue + '%')\n }\n } else if (type.toLowerCase() === 'joint'){ ///拼接sql语句查询\n ///拼接的SQL语句,keyvalue必须在scope列表中,否则不予拼接\n const result = inscope.some(item => item.toLowerCase() === matchValue.toLowerCase());\n if (result)sql = sql.replace(ele, keyValue||''); \n }\n // }\n }\n return {sql,params};\n}\n\n/**\n * 检查排序字段是否合法\n * @param {*} sortField \n * @returns \n */\nfunction sortFieldIsLegal(sortField,allowedFields = []){\n /// 没有传递排序字段,则不用检查\n if (!sortField) return sortField;\n /// 检查排序字段是否在允许的字段列表中,如果存在allowedFields,则只允许在allowedFields中排序\n if (allowedFields && allowedFields.length) {\n if(allowedFields.map(item => item.toLowerCase()).includes(sortField.toLowerCase())) return sortField;\n /// 如果不在allowedFields中,则不允许使用传入的字段名进行排序,防止sql注入\n return null;\n }\n /// 如果allowedFields为空,则检查排序的字段是否合法,防止sql注入\n if (sortField.indexOf(' ') >= 0 || sortField.indexOf('(') >= 0 || sortField.indexOf(')') >= 0) return null;\n return checkSqlInjection(sortField);\n}\n\n/*\n* 列表请求上下文中获取需要的信息\n* 如Page ,PageSize , Sort 等等\n*/\nconst getListInfo = (req, dataKey, cfgType = 0, dao) => {\n if (!dataKey) return null;\n const dataConfig = dataconfig.getConfig(dataKey, cfgType);\n if (!dataConfig?.list) return null;\n ///确认是否是需要导出Excel\n const export2Excel = (req.query.exportexcel + \"\").toLowerCase() === \"true\";\n let { page = 1, rows: pageSize = 100, sort, order, clientFilter: filter } = req.query\n ///防止sortSql 注入在排序的参数中\n if (sort) sort = sortFieldIsLegal(sort, dataConfig.list.allow_sort_fields) //checkSqlInjection(sort);\n // 防止页面数据传入非数字\n if (isNaN(pageSize)) pageSize = 30;\n // 防止页面数据传入非数字\n if (!page || isNaN(page)) page = 1\n ///最大允许获取100条数据\n pageSize =Math.max(0,Math.min(pageSize, 10000));\n ///拼接排序的语句\n if (order && sort && ORDER_STRING.includes(order.toLowerCase())) sort = sort + ' ' + order\n //req.order =req.sort? utility.ifNull((req.body.order || req.query.order), \"\"):'';\n \n if (dataConfig && dataConfig.list) {\n req.dataConfig = dataConfig\n let { sql, listsql, countsql, sqltype = 'sql', field, footer, search, sort: constsort } = dataConfig.list\n /**解析查询条件 */\n const searchCondition = getSearchCondition({ request: req, refer: search });\n /**排序方式 *///\n sort = sort || constsort;\n /**来自req请求参数中的过滤条件 */\n const clientfilter = null;// 不再支持可以通过客户端传递过滤条件,防止sql注入 //checkSqlInjection(this.parseTagInSql(req, filter, false));\n let SqlParameters = [];\n //如果配置文件中不是直接的sql语句,则从DAO对象中的指定方法来获取sql\n if (sqltype !== 'sql' && listsql && typeof (dao[listsql]) === 'function') {\n sql = dao[sql](req, { page, rows: pageSize, sort, filter: searchCondition.filter, client: clientfilter });\n if (dao[countsql] && typeof (dao[countsql]) === 'function')\n countsql = dao[countsql](req, { page, rows: pageSize, sort, filter: searchCondition.filter, client: clientfilter });\n }\n\n /**根据过滤条件、排序条件、分页获取的方式,和原始sql拼接成最终获取数据的sql */\n if (sqltype==='sql'){\n const mainParameterlizedSql = parseTagForParameterize(req, { pattern: sql, allowEmpty:true });\n if (!mainParameterlizedSql.sql) return null;\n sql = `${mainParameterlizedSql.sql} ${searchCondition.filter ||''} ${sort ? (' order by ' + sort) : ''} ${export2Excel ? '' : ' limit ' + Number(pageSize) + ' OFFSET ' + (Math.max(Number(page), 1) - 1) * Number(pageSize)};SELECT FOUND_ROWS() AS total;`;\n SqlParameters = SqlParameters.concat(mainParameterlizedSql.params || [], searchCondition.params);\n /*** 如果存在汇总列的sql,则把SQL放置在最末尾 */\n if (countsql) {\n const countParameterlizedSql = parseTagForParameterize(req, { pattern: countsql, allowEmpty: true });\n if (!countParameterlizedSql.sql) return null;\n sql += appendSearchCondition2Count(countParameterlizedSql.sql, searchCondition.filter||'')\n SqlParameters = SqlParameters.concat(countParameterlizedSql.params || [], searchCondition.params);\n }\n }\n ///如果存在统计的SQL,则参数需要Double一次\n // const sqlParams = countsql ? [].concat(searchCondition.params, searchCondition.params):searchCondition.params;\n return { sql, fields: field, params: SqlParameters, footers: footer, page, hascounter: countsql?true:false };\n }\n}\n/*\n* 详细页面请求上下文中获取需要的信息\n* 如Page ,PageSize , Sort 等等\n*/\nconst getDetailInfo = (req,dataKey) => {\n if (dataKey) {\n const dataConfig = dataconfig.getConfig(dataKey);\n if (dataConfig && dataConfig.detail) {\n req.dataConfig = dataConfig;\n const { primary, field: fields, primaryIsAutoIncrease } = dataConfig.detail;\n return { primary, fields, autoincrease: primaryIsAutoIncrease }\n }\n }\n return null;\n}\n\nmodule.exports = { \n getSearchCondition, \n parseTagInSql, \n parseTagForParameterize,\n getListInfo,\n getDetailInfo\n}","const errnum = require('./enumconst')\n\nclass ActionResult {\n constructor({ successed = true, errcode = 0, errmessage = '', data = [] }) {\n return { successed: successed, errorcode: errorcode, errmessage: errmessage, data: data }\n }\n //*为结果添加一些附加的值\n static decorateResult(result, opts) {\n Object.keys(opts).forEach(key => {\n result[key] = opts[key];\n });\n return result;\n }\n}\nActionResult.DB_CONNECTED_FAILED = { successed: false, errmessage: 'DB_CONNECTED_FAILED', errorcode: errnum.DATABASE_ERROR.DATABASE_CONNECTED_ERROR };\nActionResult.DB_EXECUTE_FAILED = { successed: false, errorcode: errnum.DATABASE_ERROR.DATABASE_EXECUTE_ERROR };\nActionResult.DB_NO_EFFECTIVE = { successed: false, errmessage: 'DB_NO_EFFECTIVE', errorcode: errnum.DATABASE_ERROR.NO_RECORD_EFFECTED };\nActionResult.DB_NO_RECORD_FOUND = { successed: false, errmessage: 'DB_NO_RECORD_FOUND', errorcode: errnum.DATABASE_ERROR.NO_RECORD_FOUND };\n\nActionResult.SUCCESS_RESULT = { successed: true, errorcode: 0 };\nActionResult.RETURN_TO_INDEX = { successed: false, errorcode: errnum.COMMON_ERROR.VISIT_TO_INDEX };\nActionResult.TOKEN_IS_EXPIRED = { successed: false, errmessage: 'TOKEN_IS_EXPIRED', errorcode: errnum.COMMON_ERROR.TOKEN_EXPIRED , total: 0, rows: [] };\nActionResult.TOKEN_IS_INVALID = { successed: false, errmessage: 'TOKEN_IS_INVALID', errorcode: errnum.COMMON_ERROR.TOKEN_IS_INVALID, total: 0, rows: [] };\nActionResult.TOKEN_IS_MISSING = { successed: false, errmessage: 'TOKEN_IS_MISSING', errorcode: errnum.COMMON_ERROR.TOKEN_IS_MISSING, total: 0, rows: [] };\nActionResult.UNAUTHORIZATION_RESULT = { successed: false, errmessage: 'UNAUTHORIZATION_RESULT', errorcode: errnum.COMMON_ERROR.UNAUTHORIZATION_ERROR, total: 0, rows: [] };\nActionResult.NO_ACCESS_RIGHT_RESULT = { successed: false, errmessage: 'NO_ACCESS_RIGHT_RESULT', errorcode: errnum.COMMON_ERROR.NO_ACCESS_RIGHT, total: 0, rows: [] };\nActionResult.API_PARAMETERS_ERROR_RESULT = { successed: false, errmessage: 'API_PARAMETERS_ERROR_RESULT', errorcode: errnum.COMMON_ERROR.API_PARAMETERS_ERROR, total: 0, rows: [] };\nActionResult.VERIFY_CODE_ERROR = { successed: false, errmessage: 'VERIFY_CODE_ERROR', errorcode: errnum.COMMON_ERROR.VERIFY_CODE_ERROR, total: 0, rows: [] };\n\nexports = module.exports = ActionResult;\n","/*\n* MySql 封装 (简单,应该尚未完善)\n*/\nconst mysql = require('mysql');\nconst apiResult = require('../actionresult');\n// const logHelper = require('doomi-helper').logHelper;\nconst { createDatabasePool } = require('./poolmanager')\nconst executeSqlWithConnection = Symbol(\"executeSqlWithConnection\");\nclass Database {\n /**\n * \n * @param {*} connectionstring \n */\n constructor(connectionstring) {\n this.pool = createDatabasePool(connectionstring);\n }\n\n /**\n * @param {{ trace: (arg0: string, arg1: any, arg2: string, arg3: any) => void; error: (arg0: string, arg1: any) => void; }} logUtility\n */\n // set logger(logUtility){\n // console.log('logUtility',logUtility)\n // this.logger = logUtility;//logHelper.getInstance().getLogger(\"framework\");\n // }\n /**\n * 防Sql注入进行编码\n * @param {*} value \n */\n escape(value) {\n return mysql.escape(value);\n }\n /**\n * 给字段名添加``\n * @param {*} value \n * @returns \n */\n escapeId(value){\n return mysql.escapeId(value)\n }\n /**\n * 记录错误日志\n */\n logError(scene, error, user = null) {\n ///不需要记录错误日志\n if (this.ingoreErrorLog === true || !this.actionLogger || typeof (this.actionLogger.logError) !== 'function') {\n return;\n }\n ///如果没有传场景,则记录数据库的业务值\n if (!scene) scene = this.constructor.name;\n this.actionLogger.logError({ scene, error, user })\n }\n /**\n * 检查是否存在数据\n * @param {*} sqlCommand \n * @param {*} parameters \n */\n async existedSqlData(sqlCommand, parameters, conn, autoclose = true) {\n let sqlExecute = await this.executeSql(sqlCommand, parameters, conn, autoclose);\n if (!sqlExecute.successed) return { successed: false }\n if (!sqlExecute.rows || sqlExecute.rows.length == 0) return { successed: true, existed: false }\n return { successed: true, existed: true, ...sqlExecute.rows[0] }\n }\n /**\n * 获取到第一行记录的所有字段的值\n * @param {*} sqlCommand \n * @param {*} parameters \n * @returns \n */\n async getComputedRowValue(sqlCommand, parameters, conn, autoclose = true) {\n let sqlExecute = await this.executeSql(sqlCommand, parameters, conn, autoclose);\n if (!sqlExecute.successed || sqlExecute.rows.length == 0) return { successed: false, errcode: -1, errmsg: '没有任何记录' }\n return { successed: true, ...sqlExecute.rows[0] }\n }\n\n /**\n * 单独获得一个连接串\n * @returns \n */\n getConnection() {\n return new Promise((success) => {\n if (!this.pool) {\n return success(null);\n }\n this.pool.getConnection(function (err, connection) {\n if (err) return success(null);;\n return success(connection)\n });\n });\n }\n /**\n * 不事务执行SQL命令\n * @param {*} sqlCommand \n * @param {*} parameters 参数\n */\n executeSql(sqlCommand, parameters, conn, autoclose = true) {\n // let logger = this.logger;\n // let that = this;\n if (conn) {\n return this[executeSqlWithConnection](sqlCommand, parameters, conn, autoclose)\n }\n return new Promise((success, failed) => {\n if (!this.pool) {\n return success(apiResult.DB_CONNECTED_FAILED);\n }\n ///创建出数据库连接,准备执行\n this.pool.getConnection(async (err, connection) => {\n if (err) {\n // if (logger) logger.error(\"Database Connected Failed :\" + err);\n return success(apiResult.DB_CONNECTED_FAILED);\n }\n let sqlResult = await this[executeSqlWithConnection](sqlCommand, parameters, connection, autoclose)\n return success(sqlResult)\n });\n });\n }\n /**\n * 使用一个已存在的链接Query Sql\n * @param {*} sqlCommand \n * @param {*} parameters \n * @param {*} conn \n * @param {*} closeAfterQuery 执行完毕后是否关闭\n */\n [executeSqlWithConnection](sqlCommand, parameters, conn, autoclose = true) {\n if (!conn) return Promise.resolve(apiResult.DB_CONNECTED_FAILED);\n return new Promise((success) => {\n // this.logger.trace(\"SqlCommand:\", sqlCommand, \"Parameters:\", parameters);\n return conn.query(sqlCommand, parameters, (err, rows) => {\n if (autoclose) conn.release();\n if (err) {\n // this.logger.error(\"Database Query Error :\" + err, sqlCommand);\n console.log('数据库操作错误', err, sqlCommand)\n this.logError(null, '数据库操作错误:' + err + sqlCommand)\n return success(Object.assign(apiResult.DB_EXECUTE_FAILED, { errmessage:'数据库操作错误'}));// err.message }));\n }\n return success({ successed: true, rows: rows });//,fields:fields});\n });\n })\n }\n /**\n * 启动事务进行保护性操作\n * @param {*} conn \n * @param {*} func \n */\n async executeSqlWithTransaction(conn, func) {\n if (!conn) {\n conn = await this.getConnection();\n }\n if (!conn) return Promise.resolve({ successed: false });\n return new Promise(success => {\n conn.beginTransaction(async err => {\n if (err) return success({ successed: false, errcode: -1, errmessage: '【事务启动错误】' + err.message });\n let result = { successed: true }\n if (func && typeof (func) === 'function') result = await func(conn);\n if (result.successed) {\n conn.commit(commiterror => {\n if (commiterror) {\n console.log('事务提交失败 :', commiterror);\n return success(Object.assign(apiResult.DB_EXECUTE_FAILED, { errmessage: commiterror.message }));\n }\n conn.release();\n return success(result);\n })\n } else {\n conn.rollback(() => {\n conn.release();\n return success(Object.assign(apiResult.DB_EXECUTE_FAILED, { errmessage: '撤回操作' }));\n })\n }\n })\n })\n }\n}\nmodule.exports = Database;","const mysql = require('mysql');\nconst appsetting = require('../../configuration/appsetting').getCurrentApp();\n/**\n * 创建和管理数据库链接池\n * @param {*} connect \n */\nlet PoolManager = {};\nmodule.exports.createDatabasePool=(connect)=>{\n if (PoolManager[connect]!=null){\n return PoolManager[connect];\n }\n const pool = mysql.createPool(appsetting.getConnection(connect || 'dev'));\n PoolManager[connect] = pool;\n return pool;\n}","/**\n * 封装了数据访问层的基础访问\n * Author : Stephen.Shen\n */\n\nconst dao = require('./mysqlbase');\nconst Moment = require('moment')\nclass mysqlDao extends dao{\n /**\n * 构造函数,确定使用的数据库链接\n * @param {{\n * database\n * permissiondatatype\n * permission\n * tableName:string\n * primaryKey:string\n * forcefilter:string\n * logicDelete:boolean\n * logicDeleteField:string\n * business:{\n * code: string\n * name: string\n * }\n * }} tableoption \n * {\n * permission:数据的权限 0:无需权限控制 1:控制权限 \n * permissiondatatype:权限控制的业务数据类型\n * tableName:操作的数据表名称\n * primaryKey: 表的主键名称\n * logicDelete:表记录是否逻辑删除,默认逻辑删除\n * logicDeleteField:代表逻辑删除的字段名称\n * forcefilter:强制添加的sql附加语法,会添加在根据主键获取、修改、删除的尾部,加强操作的安全性验证\n * }\n */\n constructor(tableoption){\n //super(appsetting.getConnection('dev'));\n super(tableoption ? (tableoption.database || 'dev') : 'dev');\n if (tableoption){\n tableoption.forcefilter=tableoption.forcefilter || '';\n this.tableoption = tableoption;\n } \n }\n /**\n * 数据对象是否存在权限因子控制\n */\n get hasPermissionControl(){\n if (!this.tableoption) return false;\n return this.tableoption.permission && !isNaN(this.tableoption.permissiondatatype);\n }\n /**\n * 获取列表的权限控制Sql条件\n */\n get permissionSql(){\n if (this.hasPermissionControl){\n const leftjoin = `left join vmv3_data_permission vp on vp.data_type = ${this.tableoption.permissiondatatype} \n and ${this.tableoption.primaryKey} = vp.data_id \n and vp.permission_type = 2`\n return `\n if (ifnull(vp.data_department, '') = '', ' and 1 = 1 ', ' and find_in_set('@user.department@',vp.data_department)')\n if (ifnull(vp.data_role, '') = '', ' and 1 = 1 ', ' and find_in_set('@user.role@',vp.data_role)')\n if (ifnull(vp.data_department, '') = '', ' and 1 = 1 ', ' and find_in_set('@user.id @',vp.data_user)')\n `\n }\n return '';\n }\n /**\n * 返回本数据实体对应的业务名称\n */\n getBusiness(){\n if (this.tableoption) return this.tableoption.business;\n return null;\n }\n /**\n * 通过sql获取数据\n * @param {*} sqlString \n * @param {*} parameters \n */\n async loadData(sqlString, parameters){\n return this.executeSql(sqlString, parameters);\n }\n /**\n * \n * @returns {string} \n * @summary 根据主键获取数据\n */\n getByIdSql(){\n return `select * from ${this.tableoption.tableName} where ${this.tableoption.primaryKey}=? ${this.tableoption.forcefilter}`;\n }\n /**\n * 更改记录\n */\n updateSql(id) { \n return `update ${this.tableoption.tableName} set ? where ${this.tableoption.primaryKey}=? ${this.tableoption.forcefilter}`;\n }\n /**\n * 新增记录\n */\n insertSql() { \n return `insert into ${this.tableoption.tableName} set ?`; \n }\n /**\n * 删除记录\n */\n deleteSql() { \n // const ids = (id + '').trim().split(',').map(x => '\\'' + x + '\\'');\n ////如果是逻辑删除,则只将记录的删除状态设置为1\n if(this.tableoption.logicDelete) {\n\n let sqlDelete = `update ${this.tableoption.tableName} set #DELETEBY# #DELETEDATE# ${this.tableoption.logicDeleteField || 'rec_isdeleted'} =1 where ${this.tableoption.primaryKey} =? ${this.tableoption.forcefilter}`; \n sqlDelete = sqlDelete.replace('#DELETEBY#', this.tableoption.logDeleteBy?`${this.tableoption.logDeleteBy}=?,`:'')\n sqlDelete = sqlDelete.replace('#DELETEDATE#', this.tableoption.logDeleteDate ? `${this.tableoption.logDeleteDate}=now(),` : '');\n return sqlDelete;\n }\n return `delete from ${this.tableoption.tableName} where ${this.tableoption.primaryKey} =? ${this.tableoption.forcefilter}`; \n }\n\n /**\n * 批量操作Sql\n */\n BatchSql() { \n return `update ${this.tableoption.tableName} set ? where find_in_set(${this.tableoption.primaryKey},?) ${this.tableoption.forcefilter}`; \n }\n\n ///根据主键获取一条记录\n async getBykey(Sql, id) {return this.executeSql(Sql, id);}\n ///插入记录\n async create(Sql, model) {return this.executeSql(Sql, model);}\n ///更新记录\n async update(Sql, model, id) {return this.executeSql(Sql, [model, id]);}\n ///删除记录\n async delete(Sql, id,userid) { \n const ids = (id + '').trim().split(',').map(x => '\\'' + x + '\\'');\n if (this.tableoption.logicDelete && this.tableoption.logDeleteBy){\n return this.executeSql(Sql, [userid, id]); //ids.join(',')]); \n }\n return this.executeSql(Sql, id); //ids.join(',')); \n ///\n //return this.executeSql(Sql, id); \n /*if (result.successed && this.tableoption.logicDelete && userid && (this.tableoption.logDeleteBy || this.tableoption.logDeleteDate)){\n let sqlLog = `update ${this.tableoption.tableName} set ? where ${this.tableoption.primaryKey}=? ${this.tableoption.forcefilter}`; \n let model = {};\n if (this.tableoption.logDeleteBy){\n model[this.tableoption.logDeleteBy] = userid;\n }\n if (this.tableoption.logDeleteDate){\n model[this.tableoption.logDeleteDate] = Moment().format('YYYY-MM-DD HH:mm:ss');\n }\n if (Object.keys(model).length>0) this.executeSql(sqlLog, [model, id]);\n }\n return result;\n */\n }\n /**\n * 获取对应数据的权限设置\n * @param {*} id \n */\n async getDataPermissionSetting(id,busSql){\n ///没有权限控制,则无需获取单条数据的权限因子\n if (!this.hasPermissionControl){\n return null;\n }\n // const sqlCommand = `select \n // data_type as datatype,\n // data_id as id,\n // permission_type as permissiontype,\n // data_department as department,\n // data_department_text as departmenttext,\n // data_role as role,\n // data_role_text as roletext,\n // data_level as level,\n // data_level_text as leveltext,\n // data_user as user,\n // data_user_text as usertext\n // from vmv3_data_permission \n // where data_type=? \n // and data_id=?\n // `\n // return this.executeSql(sqlCommand, [this.tableoption.permissiondatatype,id])\n // .then(result=>{\n // let retValue = {\n // successed:true,\n // managepermission: {\n // datatype:this.tableoption.permissiondatatype,\n // id,\n // permissiontype:1,\n // department:'',\n // departmenttext:'',\n // role:'',\n // roletext:'',\n // level:'',\n // leveltext:'',\n // user:'',\n // usertext:''\n // },\n // consumepermission: {\n // datatype: this.tableoption.permissiondatatype,\n // id,\n // permissiontype: 2,\n // department: '',\n // departmenttext: '',\n // role: '',\n // roletext: '',\n // level: '',\n // leveltext: '',\n // user: '',\n // usertext: ''\n // }\n // };\n // result.rows.forEach(element => {\n // if (element.permissiontype === 1) {////管理权限\n // retValue.managepermission = element;\n // } else if (element.permissiontype === 2) {////消费权限\n // retValue.consumepermission = element;\n // }\n // });\n // return retValue;\n // })\n const sqlCommand = `select \n data_id as id,\n data_type as datatype,\n allow_type as allowtype,\n allow_id as allowid,\n allow_name as allowname\n from framework_permission \n where \n data_id=?\n and data_type=? \n ${busSql}\n order by allow_type,allow_id\n `\n return this.executeSql(sqlCommand, [id,this.tableoption.permissiondatatype])\n .then(result=>{\n let retValue = {\n successed:true,\n managepermission: {},\n consumepermission: {\n datatype: this.tableoption.permissiondatatype,\n id,\n permissiontype: 2,\n }\n };\n let pObject = {deptid:[],depttext:[],roleid:[],roletext:[],userid:[],usernames:[]}\n for (const element of result.rows){\n switch (element.allowtype){\n case 1: ///部门\n pObject.deptid.push(element.allowid)\n pObject.depttext.push(element.allowname)\n break;\n case 2: ///角色\n pObject.roleid.push(element.allowid)\n pObject.roletext.push(element.allowname)\n break;\n case 4: ///用户\n pObject.userid.push(element.allowid)\n pObject.usernames.push(element.allowname)\n break;\n }\n }\n retValue.consumepermission.department = pObject.deptid.join(',')\n retValue.consumepermission.departmenttext = pObject.depttext.join(',') ;//+ ((pObject.deptid.length > pObject.depttext.length) ? `等${pObject.deptid.length}个部门`:'');\n\n retValue.consumepermission.role = pObject.roleid.join(',')\n retValue.consumepermission.roletext = pObject.roletext.join(',');// + ((pObject.roleid.length > pObject.roletext.length) ? `等${pObject.roleid.length}个角色` : '');\n\n retValue.consumepermission.user = pObject.userid.join(',')\n retValue.consumepermission.usertext = pObject.usernames.join(',');// + ((pObject.userid.length > pObject.usernames.length) ? `等${pObject.userid.length}个用户` : '');\n\n // console.log('retValue==>', retValue)\n return retValue;\n })\n }\n\n async saveDataPermissionSetting(id,permissionParam){\n if (!this.hasPermissionControl || !permissionParam) {\n return Promise.resolve({successed:true})\n };\n let sqlCommand = `delete from framework_permission where data_id=? and data_type=?;`\n let subItem = [];\n \n\n if (permissionParam.consumepermission) {\n const mItem = permissionParam.consumepermission;\n const deptids = mItem.department?mItem.department.split(','):[]\n for (const deptid of deptids){\n subItem.push([id, this.tableoption.permissiondatatype, 1, deptid])\n }\n const roleids = mItem.role ? mItem.role.split(',') : []\n for (const rid of roleids) {\n subItem.push([id, this.tableoption.permissiondatatype, 2, rid])\n }\n const userids = mItem.user ? mItem.user.split(',') : []\n for (const uid of userids) {\n subItem.push([id, this.tableoption.permissiondatatype, 4, uid])\n }\n }\n let sqlParam = [id, this.tableoption.permissiondatatype];\n if (subItem.length){\n sqlCommand = sqlCommand+`\n insert into framework_permission(\n data_id,\n data_type,\n allow_type,\n allow_id\n ) values ?;\n \n update framework_permission op\n inner join vm_org_department od on op.allow_id=od.department_id\n set op.allow_name = od.department_name,\n op.allow_path = od.parent_path\n where data_id=? and data_type=? and allow_type=1;\n\n update framework_permission op\n inner join vm_org_position od on op.allow_id=od.position_id\n set op.allow_name = od.position_namecn\n where data_id=? and data_type=? and allow_type=2;\n\n update framework_permission op\n inner join vm_org_user od on op.allow_id=od.user_id\n set op.allow_name = od.user_name\n where data_id=? and data_type=? and allow_type=4;\n `\n sqlParam.push(\n subItem,\n id,\n this.tableoption.permissiondatatype,\n id,\n this.tableoption.permissiondatatype,\n id,\n this.tableoption.permissiondatatype);\n }\n return this.executeSql(sqlCommand, sqlParam);\n }\n /**\n * \n * @param {*} model 需要改变的属性键值对\n * @param {*} id 批量操作的id集合,逗号分开\n */\n async batchUpdate(Sql,model,id,userid){\n ////记录批量删除的人\n if (this.tableoption.logicDelete && this.tableoption.logDeleteBy && model[this.tableoption.logicDeleteField || 'rec_isdeleted']!=null ) {\n model[this.tableoption.logDeleteBy] = userid;\n if (this.tableoption.logDeleteDate){\n model[this.tableoption.logDeleteDate] = Moment().format('YYYY-MM-DD HH:mm:ss');\n }\n }\n return this.executeSql(Sql, [model, id])\n .then(result=>{\n return {successed:true,count:result.rows.affectedRows }\n }) \n }\n}\nexports=module.exports = mysqlDao;\n","/* \n* Controller 基类\n* 所有Node编写的业务处理控制类都集成此基类,路由的配置直接配置在roterConfig.json中\n* 功能:\n* 基类主要实现了数据基础的增删改查的基本操作,如无特殊业务逻辑子类已无需再\n* 重新实现,如有特殊的业务可以重写几个方法\n*/\nconst express = require('express');\nconst {Data2View,View2Data} = require('../utilities/transferutility');\nconst ExcelUtility = require('../utilities/excelutility');\nconst constEnum = require('./enumconst');\nconst { getListInfo, getDetailInfo, parseTagInSql } = require('../utilities/requestparser');\nconst apiResult = require('./actionresult');\nconst daoBase = require('./database/daoBase');\nconst exportUtility = ExcelUtility.getInstance();\n\nclass controller {\n /**\n * 构造函数,每个Controller传递进来本业务的数据访问实例\n * @param {*} application app 对象\n * @param {*} dao DAO层\n */\n constructor(application, dao) {\n this.app = application;\n ///高速缓存\n this._redisHelper = this.app.redis;\n ///日志记录器\n this.logger = this.app.logger;\n ///用户行为记录器\n this.actionLogger = this.app.actionLogger;\n ///需要数据访问实体的实例\n this._daoModel = dao?dao:new daoBase();\n this._daoModel.actionLogger = this.actionLogger;\n this._daoModel.logger = application.logger;\n this._router = express.Router();\n ///实现的集成类中只需要去重写此方法\n this.initializeRouter(this);\n\n }\n get router() { return this._router; }\n get baseUrl() { return null };\n /**\n * 权限的业务sql过滤\n */\n PermissonBusiness(_req){\n return null;\n }\n /**\n * 导出数据到Excel 中\n * @param {*} data \n * @param {*} excelkey \n */\n async export2Excel(data,excelkey) {\n let excelResult = await exportUtility.recordset2ExcelFile(data,excelkey, this.beforeExportExcel)\n return excelResult;\n }\n /**\n * 导出数据到Excel的多个workseet中\n * @param {*} data \n * @param {*} excelkey \n */\n async export2MutlisheetExcel(datainfo) {\n if (!Array.isArray(datainfo) || datainfo.length == 0) return {successed:false};\n let excelResult = await exportUtility.recordset2MutlisheetExcelFile(datainfo, this.beforeExportExcel)\n return excelResult;\n }\n /**\n * 写入Excel数据\n * @param {*} data \n * @param {*} excelkey \n * @returns \n */\n async writeExcel(data, excelkey){\n let excelResult = await exportUtility.writeExcel(data, excelkey)\n return excelResult;\n }\n /**\n * 记录用户的操作行为\n * req:HttpRequest\n * business:业务信息\n * action:操作的行为\n * successed:操作是否成功\n * \n */\n logUserAction(req,business,action,successed=0,memo=null){\n if (this.actionLogger && business && action) this.actionLogger.log(req,business,action,successed,memo)\n }\n /**\n * 创建基于CRUD的基础路由方式\n * @param {*} actionType \n * @param {*} req \n * @param {*} res \n */\n createCRUDRoute(actionType,url,datakey,middleware){\n let instance = this;\n instance.router[actionType.method](url, middleware ? middleware : (req, res, next)=>{return next()},async (req,res)=>{\n ////执行CRUD之前,可由继承的子类实现规则验证\n ////如果返回successed:false,则不再继续\n let beforeResult = await instance.beforeCRUD(actionType,req,res)\n if (!beforeResult.successed) return res.json(beforeResult);\n ////具体执行基类的CRUD方法\n let result;\n if (actionType.method==='delete')\n result = await instance.delete(req,req.params.id);\n else\n result = await instance[actionType.func](req, datakey);\n ////执行完CRUD方法之后的处理\n result = await instance.afterCRUD(result,actionType,datakey,url,req,res)\n return res.json(result)\n })\n }\n /**\n * 快速构造Controller中的CRUD各个路由,大部分基础表都可复用\n * @param {*} url ////基础地址,根据RESTFUL的风格生成CRUD风格的\n * CREATE : POST url \n * UPDATE : PUT url/{id} \n * LIST : GET url \n * DELETE : DELETE url/{id}\n * @param {*} datakey 对应在dataconfig.json中的key,方便实体和传递的数据的映射以及SQL\n * @param {*} action 操作的组合 CRUDS\n */\n initializeCRUDRouter(url, datakey, action = 'SCRUD', middleware){\n if(!url || !datakey) return;\n let urlWithId = url.endsWith('/')?`${url}:id`:`${url}/:id`;\n if (action.indexOf('C') >= 0) this.createCRUDRoute(constEnum.CRUDAction.Create, url, datakey, middleware)\n if (action.indexOf('S') >= 0) this.createCRUDRoute(constEnum.CRUDAction.Single, urlWithId, datakey, middleware)\n if (action.indexOf('R') >= 0) this.createCRUDRoute(constEnum.CRUDAction.Retrieve, url, datakey, middleware)\n if (action.indexOf('U') >= 0) this.createCRUDRoute(constEnum.CRUDAction.Update, urlWithId, datakey, middleware)\n if (action.indexOf('D') >= 0) this.createCRUDRoute(constEnum.CRUDAction.Delete, urlWithId, datakey, middleware)\n }\n /**\n * CRUD真正进入数据库之前的处理,可由继承的类来处理\n * 不处理则默认返回继续\n * @param {*} result \n * @param {*} action \n */\n async beforeCRUD(_action, _req,_res){\n return {successed:true}\n }\n /**\n * CRUD执行数据库之后的处理,可由继承的类来处理\n * @param {*} result \n * @param {*} action \n */\n async afterCRUD(result,_action,_datakey,_url, _req,_res){\n return result;\n }\n /*\n * 初始化路由处理器(空方法,待继承的子类去实现)\n * 除了在routerConfig中配置的路由以外,继承的子类可以重写实现此方法来\n * 继续配置你的路由\n */\n initializeRouter(_instance) { }\n /*\n * 数据加载之前的动作\n * 子类可以重写该方法\n */\n async beforeAccessDB(_req, sql, sqlParams, _type, _instance) {\n return { sql: sql, sqlParams: sqlParams, canceled: false };\n }\n /**\n * 数据导出到Excel之前可以由继承类再进行处理\n * @param {*} dataOption \n */\n beforeExportExcel(dataOption) {\n return dataOption;\n }\n /**\n * 执行批量操作更新\n * @param {*} model 需要更新的字段和值\n */\n async batchUpdate(req,model,id){\n if (!id) id = req.params.id;\n if (!id) return {successed:false,errcode:-2,errmsg:'缺失批量操作的id'}\n let batchSql = parseTagInSql(req,this._daoModel.BatchSql());\n let result = await this._daoModel.batchUpdate(batchSql, model, id, req.user?.id)\n this.logUserAction(req,this._daoModel.getBusiness(),6,result.successed?0:-1);\n return result;\n }\n /*\n * 获取查询列表记录的方法\n */\n async getListData(req, dataKey, configFile = 0) {\n if (this.logger) this.logger.trace(\"准备获取dataconfig文件中对应的 %s list数据\",dataKey)\n const listinfo = getListInfo(req, dataKey, configFile, this._daoModel); //, ignorefilter==1\n if (!listinfo) return { successed: false, errcode: -10, errmsg:`缺失${dataKey}对应的查询语句`};\n\n ////直接操作数据库之前,可由子类再次Handler\n let beforeData = await this.beforeAccessDB(req, listinfo.sql, listinfo.params, \"list\", this);\n ////如果返回Null,则表示不加载数据了\n if (beforeData.canceled === true) return { successed: false, errorcode: 1, errmsg: \"操作取消\" };\n ////操作数据库\n let result = await this._daoModel.loadData(beforeData.sql, beforeData.sqlParams);\n if(!result.successed) {\n ////失败也需要记录\n if (req.query.exportexcel==='true') this.logUserAction(req,this._daoModel.getBusiness(),5,-1);\n return result;\n }\n ///从数据库中获取到了原始数据\n if (result.rows) {\n ///将从数据库中获得的结果集根据dataconfig中的配置进行映射转换\n let resultItem = Data2View(result.rows[0], listinfo.fields)\n ///输出的结果是否需要装饰带有successed,total等,便于列表\n let outputData = { successed: true, page: listinfo.page, rows: resultItem.data };\n ///需要进行尾部统计的列表\n if (listinfo.hascounter) {\n let footerItem = Data2View(result.rows[2], listinfo.footers)\n outputData.footer = footerItem.data;\n }\n outputData.total = await this.getListRecordCount(result);\n ///处理导出Excel\n if (req.query.exportexcel==='true') {\n outputData= await this.export2Excel(outputData.rows,req.query.excelkey || dataKey)\n this.logUserAction(req,this._daoModel.getBusiness(),5,0);\n }\n return outputData;\n }\n return {successed:false, errcode: -1, total: 0, rows: [] };\n }\n /**\n * 返回数据结果的记录总数\n * @param {*} data \n */\n async getListRecordCount(result){\n return result.rows[1][0].total;\n }\n /*\n * 获取详细记录的方法\n */\n async getDataById(req, dataKey, sqlCommand,idValue) {\n if (this.logger) this.logger.trace(\"准备获取dataconfig文件中对应的 %s 详细数据\",dataKey)\n const detailinfo = getDetailInfo(req, dataKey);\n if (!detailinfo) return { successed: false, errcode: -10, errmsg: `缺失${dataKey}对应的详情配置` };\n let beforeData = await this.beforeAccessDB(req, sqlCommand || this._daoModel.getByIdSql(), idValue ||req.params.id, \"detail\", this);\n ////如果返回Null,则表示不加载数据了\n if (beforeData.canceled===true) return { successed: false, errorcode: 1, errormessage: \"操作已取消\" };\n /////处理SQL中的一些定义符\n let parseSql = parseTagInSql(req,beforeData.sql);\n ////操作数据库\n let result = await this._daoModel.getBykey(parseSql, beforeData.sqlParams);\n if (!result.successed) return result;\n if (result.rows && result.rows.length == 1) {\n ///如果对象有数据权限控制,则需要插入\n ///提交的权限设置\n ///将从数据库中获得的结果集根据dataconfig中的配置进行映射转换\n let resultMapping = Data2View(result.rows, detailinfo.fields);\n ///如果业务对象具备权限控制的业务,则需要将该数据的所赋予的权限对象加载出来\n if (this._daoModel.hasPermissionControl) {\n const accessResult = await this._daoModel.getDataPermissionSetting(req.params.id,this.PermissonBusiness(req))\n if (accessResult.successed) {\n resultMapping.data[0].managepermission = accessResult.managepermission;\n resultMapping.data[0].consumepermission = accessResult.consumepermission;\n }\n }\n return { successed: true, rows: resultMapping.data[0], id: req.params.id };\n }\n return apiResult.DB_NO_RECORD_FOUND;\n }\n /*\n * 新增实体记录的方法\n */\n async create(req, dataKey, sqlCommand) {\n if (this.logger) this.logger.trace(\"准备根据dataconfig文件中对应的 %s 配置插入数据\",dataKey)\n let mapping = req.query.Mapping??true; //|| 'true'==='true' ;//commonHelper.ifNull(req.query.Mapping, true);\n let detailinfo, resultItem = { successed: true, data: req.body };\n ///是否需要将data中的key-value值到配置文件中进行转换\n if (mapping == true) {\n detailinfo = getDetailInfo(req, dataKey);\n if (!detailinfo) return { successed: false, errcode: -10, errmsg: `缺失${dataKey}对应的详情配置` };\n resultItem = View2Data(req, detailinfo.fields, \"create\");\n ///如果转换的验证过程中出现错误,则返回\n if (!resultItem.successed) return resultItem;\n }\n let beforeData = await this.beforeAccessDB(req, sqlCommand || this._daoModel.insertSql(), resultItem.data, \"create\", this);\n ////如果返回Null,则表示不加载数据了\n if (beforeData.canceled) return { successed: false, errorcode: 1, errormessage: \"操作取消\" };\n if (this.logger) this.logger.trace(\"插入数据准备 : \",beforeData)\n let result = await this._daoModel.create(beforeData.sql, beforeData.sqlParams, req)\n if(!result.successed) {\n this.logUserAction(req,this._daoModel.getBusiness(),1,-1);\n return result;\n }\n let primaryKey;\n if (mapping && detailinfo.primary) {\n ///自动增长的主键字段\n if (detailinfo.autoincrease === true) primaryKey = result.rows.insertId;\n else {\n if (typeof (detailinfo.primary) === \"string\") primaryKey = beforeData.sqlParams[detailinfo.primary];\n if (typeof (detailinfo.primary) === \"object\")\n primaryKey = detailinfo.primary.map(element => { return beforeData.sqlParams[element]; });\n }\n }\n ///如果对象有数据权限控制,则需要插入\n ///提交的权限设置\n if (this._daoModel.hasPermissionControl){\n let param = {}\n if (req.body.managepermission) \n param.managepermission = JSON.parse(req.body.managepermission);\n else\n param.managepermission= {};\n if (req.body.consumepermission) \n param.consumepermission = JSON.parse(req.body.consumepermission);\n else\n param.consumepermission = {}\n this._daoModel.saveDataPermissionSetting(primaryKey, param)\n }\n this.logUserAction(req,this._daoModel.getBusiness(),1,0);\n return { successed: true, data: resultItem.data, id: primaryKey };\n }\n /*\n * 修改实体记录的方法\n */\n async update(req, dataKey, sqlCommand, id) {\n if (this.logger) this.logger.trace(\"准备根据dataconfig文件中对应的 %s 配置修改数据\",dataKey)\n if (id == null) id = req.params.id;\n let mapping = req.query.Mapping??true;// commonHelper.ifNull(req.query.Mapping, true);\n let detailinfo, resultItem = { successed: true, data: req.body };\n ///是否需要将data中的key-value值到配置文件中进行转换\n if (mapping == true) {\n detailinfo = getDetailInfo(req, dataKey);\n if (!detailinfo) return { successed: false, errcode: -10, errmsg: `缺失${dataKey}对应的详情配置` };\n ///从Request中获取到用户提交的数据\n resultItem = View2Data(req, detailinfo.fields, \"update\");\n }\n ///如果不需要转换,则直接使用前端提交上来的值\n let beforeData = await this.beforeAccessDB(req, sqlCommand || this._daoModel.updateSql(), resultItem.data, \"update\", this);\n ////如果返回Null,则表示不加载数据了\n if (beforeData.canceled) return { successed: false, errorcode: 1, errormessage: \"操作取消\" };\n if (this.logger) this.logger.trace(\"修改数据准备 : \",beforeData)\n /////处理SQL中的一些定义符\n let parseSql = parseTagInSql(req,beforeData.sql);\n let result = await this._daoModel.update(parseSql, beforeData.sqlParams, id);\n if(!result.successed) {\n this.logUserAction(req,this._daoModel.getBusiness(),3,-1);\n return result;\n }\n ///更新成功\n if (result.rows.affectedRows == 1) {\n ///如果对象有数据权限控制,则需要插入\n ///提交的权限设置\n if (this._daoModel.hasPermissionControl) {\n let param = {}\n if (req.body.managepermission) \n param.managepermission = JSON.parse(req.body.managepermission);\n else\n param.managepermission = {}\n if (req.body.consumepermission) \n param.consumepermission = JSON.parse(req.body.consumepermission);\n else\n param.consumepermission = {}\n this._daoModel.saveDataPermissionSetting(id, param)\n }\n this.logUserAction(req,this._daoModel.getBusiness(),3,0);\n return { successed: true, data: resultItem.data, id: id };\n }\n ///更新失败\n return apiResult.DB_NO_EFFECTIVE; //{successed:false,errorcode:errorcode.DATABASE_ERROR.NO_RECORD_EFFECTED,data:resultItem.data};\n }\n\n /*\n * 删除实体记录的方法\n */\n async delete(req, id, sqlCommand) {\n if (this.logger) this.logger.trace(\"准备删除数据\",id)\n let beforeData = await this.beforeAccessDB(req, sqlCommand || this._daoModel.deleteSql(id), id, \"delete\", this);\n ////如果返回Null,则表示不加载数据了\n if (beforeData.canceled) return { successed: false, errorcode: 1, errormessage: \"操作取消\" };\n /////处理SQL中的一些定义符\n let parseSql = parseTagInSql(req,beforeData.sql);\n ////操作数据库\n let result = await this._daoModel.delete(parseSql, beforeData.sqlParams,req.user?.id)\n if(!result.successed) {\n this.logUserAction(req,this._daoModel.getBusiness(),2,-1);\n return result;\n }\n this.logUserAction(req,this._daoModel.getBusiness(),2,0);\n return { successed: true, id: id, count: result.rows.affectedRows };\n }\n}\nexports = module.exports = controller;","const { parseKeyValue, formatValue, validatorParamsType } = require('./keywordparse');\n/**\n* 将结果转化为Mapping对应的键值输出\n* @param {*} originalResult \n* @param {*} fieldConfig \n* @returns transferName2Mapping\n*/\nconst Data2View = (originalResult, fieldConfig) => {\n if (!originalResult) return { successed: true, data: null };\n if (!fieldConfig || fieldConfig.length == 0) return { successed: true, data: originalResult };//return success({successed:true,data:originalResult});\n\n let retResult = [];\n for (const row of originalResult) {\n let item = {};\n for (const element of fieldConfig) {\n ///如果该字段的序列化仅用于向后保存,则序列化到\n ///前端页面的时候就不再输出了\n if (element.direction == \"backonly\") continue;\n let rawValue = row[element.name];\n if (!rawValue && element.nullValue) rawValue = element.nullValue;\n ///格式化输出\n if (element.format) {\n rawValue = formatValue(rawValue, element.format)\n }\n item[element.mapping || element.name] = rawValue;\n }\n retResult.push(item);\n }\n return { successed: true, data: retResult };\n\n}\n/**\n * 数据准备保存到数据库中,从视图提交的数据中进行转换\n * @param {*} req \n * @param {*} fieldConfig \n * @param {*} doWhat \n * @returns transferMapping2Name\n */\nconst View2Data = (req, fieldConfig, doWhat) => {\n let model = {}, tmpModel = {};\n // var ingoreKey = req.query.ingoreNullKey != null && req.query.ingoreNullKey == 'true';\n if (Array.isArray(fieldConfig)) {\n for (const element of fieldConfig) {\n ///如果该字段的序列化仅用于向前端输出,保存时忽略\n if (element.direction == \"frontonly\") continue;\n if (element.action && element.action.indexOf(doWhat) < 0) continue;\n let bodyKey = element.mapping || element.name;\n let postValue = req.body[bodyKey];\n ////body中没有这个属性\n //&& element.ignoreundefined == true\n if (postValue === undefined) {\n if ((doWhat == 'update' && !element.required) ||\n (doWhat == 'create' && !element.required && !element.default && !element.nullValue))\n continue;\n }\n ///去除两边的空格,默认是去掉空格\n if (typeof (postValue) === 'string') {\n if ((!element.trim || element.trim == true)) postValue.trim();\n if (element.maxlength && postValue.length > element.maxlength) {\n return { successed: false, errcode: 6, errmsg: '输入的长度超出,最大允许' + element.maxlength, name: element.mapping }\n }\n }\n\n ///如果提交的值为空\n if (!postValue) { // if (commonHelper.isNullOrEmpty(postValue)) {\n if (element.nullValue)\n postValue = parseKeyValue(req, element.nullValue);\n else\n postValue = null;\n }\n if (!postValue && element.default) postValue = element.default;\n ///不允许为空值\n if (element.required === true && !postValue) return { successed: false, errcode: 5, errmsg: '请填写必填字段内容', name: bodyKey }\n // //空值则不替换或不设置该字段\n // if (!postValue && element.ignorenull===true){\n // continue;\n // }\n //验证值的类型是否正确,主要验证是否数字\n if (element.type && postValue && !validatorParamsType(postValue, element.type)) {\n return { successed: false, errcode: 4, errmsg: `提交的值与要求的类型不匹配:(${bodyKey},${element.type})`, name: bodyKey }\n }\n ///格式化结果 : 这个可以用,暂时先去掉\n // if (postValue && element.format) {\n // if (stringHelper.startWith(element.format, '{') && stringHelper.endsWith(element.format, '}'))\n // postValue = stringHelper.format(element.format, postValue);\n // else {\n // postValue = ViewHelper.specialFormatValue(element.format, postValue, false);\n // }\n // }\n ////这个字段是否需要放在其他对象中\n if (element.model) {\n let modelitem = tmpModel[element.model] || {};\n modelitem[element.name] = postValue;\n tmpModel[element.model] = modelitem;\n }\n else\n model[element.name] = postValue;\n }\n\n }\n else\n model = req.body;\n req.modellist = tmpModel;\n return { successed: true, data: model };\n}\n\nmodule.exports = {\n Data2View,\n View2Data\n}","import { getDefaultExportFromCjs } from \"\u0000commonjsHelpers.js\";\nimport { __require as requireFramework } from \"/Users/stephen/01.Work/02.doomisoft/doomiframework/framework/index.js\";\nvar frameworkExports = requireFramework();\nexport { frameworkExports as __moduleExports };\nexport default /*@__PURE__*/getDefaultExportFromCjs(frameworkExports);","exports = module.exports = {\n doomiwork:require('./core/doomiwork'),\n controller: require('./core/controller'),\n model: require('./core/database/daoBase'),\n appsetting:require('./configuration/appsetting'),\n actionresult:require('./core/actionresult'),\n excelutility:require('./utilities/excelutility'),\n tokenHelper:require('./utilities/tokenutility'),\n constants:require('./core/enumconst'),\n}\n","/**\n * 后台路由授权访问的Token验证\n */\n// const cache = require('doomi-helper').redisHelper.getInstance();\nclass TokenUtility {\n constructor(cacheinstance){\n this.cache = cacheinstance;\n }\n setToken(token, tokenObject, expire) {\n // if (typeof tokenObject != \"string\") tokenObject = JSON.stringify(tokenObject);\n return this.cache.set(token, tokenObject, expire);\n }\n ///从缓存中获取用户\n async getToken(token,isObject=true) {\n let value = await this.cache.get(token);\n if (!value) return value;\n return isObject ? JSON.parse(value) : value;\n }\n /**\n * token是否有效\n * @param {*} token \n */\n async tokenIsValid(token){\n return (await this.getToken(token,false))!=null\n }\n /**\n * 删除Token\n * @param {*} token \n */\n deleteToken(token){\n this.cache.delete(token);\n }\n /**\n * 延长token的有效期\n * @param {*} token \n * @param {*} tokenObject \n * @param {*} expire \n */\n extendToken(token,expire) {\n return this.cache.expire(token,expire);\n }\n}\nexports = module.exports.TokenHelper = (cacheinstance)=>{\n return new TokenUtility(cacheinstance)\n};"],"names":["path","require$$0","fs","require$$1","appsetting","constructor","config","process","env","CONFIGFILE","configfile","join","cwd","existsSync","Error","this","settingjson","require","getCurrentApp","app","getSetting","settingKey","defaultValue","getSection","sectionName","getConnection","connName","connections","module","loadController","IGNORE_FOLDER","loadFolderFiles4Router","result","startPath","routeGroup","exceptFile","exceptfile","exceptfolder","scanFolder","folder","getFolderControllerFiles","execfiles","execfolder","files","readdirSync","val","fPath","stats","statSync","isDirectory","indexOf","fileName","findFolderFiles","isFile","fileExtion","extname","toLowerCase","basename","substr","length","push","baseFolder","includes","routes","Array","isArray","startupRoot","element","disabled","include","includeRouteJson","console","log","modules","baseUrl","groupName","routefolder","Interceptor","use","controller","modulePath","router","routerconfig","require$$2","require$$3","Doomiwork","startWork","application","option","redis","logaction","actionLogger","logger","req","res","next","user","headers","monitor","registerMonitorRouter","roterfile","get","_req","packjson","name","version","json","successed","message","post","async","question","content","__doomiwork__token__","body","status","send","FuncResult","failed","filepath","resolve","writeFileSync","encoding","flag","registerUrlInterceptor","intrupFilter","registerGroupInterceptor","randomUUID","moment","keywordparse","parseKeyValue","str","strItems","split","collection","query","params","id","appid","orgnizations","format","validatorParamsType","value","dataType","inscope","isNaN","date","Date","parse","datetime","inRange","item","some","scope","formatValue","replace","xlsx","uuid","ExcelUtility","exportFolder","excelConfig","getInstance","instance","readExcel","excelObj","data","createExcelBuffer","workSheetName","buffer","build","set","encodeURI","fReadStream","createReadStream","on","chunk","write","end","writeExcel","sheetName","randomFile","_saveDir","dirname","mkdirsSync","success","errorcode","errmessage","Promise","reslove","writeFile","err","recordset2ExcelFile","dataRow","exportConfig","readyDataFunc","setting","dataBuffer","worksheetName","fieldKey","titleRow","worksheet","columns","forEach","field","dataOption","type","title","firstRow","Object","keys","key","rowItem","writeMutlisheetExcel","sheetinfo","recordset2MutlisheetExcelFile","sheetsInfo","_instance","mapping","dirpath","mode","pathtmp","splitPath","sep","nLoop","mkdirSync","enumconst","DATABASE_ERROR","DATABASE_CONNECTED_ERROR","DATABASE_EXECUTE_ERROR","NO_RECORD_EFFECTED","NO_RECORD_FOUND","COMMON_ERROR","TRANSMIT_TO_VIEW_ERROR","TRANSMIT_TO_DATA_ERROR","VISIT_TO_INDEX","API_PARAMETERS_ERROR","VERIFY_CODE_ERROR","NO_ACCESS_RIGHT","TOKEN_IS_MISSING","TOKEN_EXPIRED","TOKEN_IS_INVALID","UNAUTHORIZATION_ERROR","LOGIN_ERROR","SUCCESSED","USER_NOT_FOUND","USER_PASSWORD_ERROR","SERIAL_CODE_ERROR","UNKNOW_ERROR","GET_USERINFO_ERROR","CRUDAction","Create","method","func","Retrieve","Single","Update","Delete","dataConfig","comcfgfile","cache","commoncache","getConfig","itemName","cfgType","getDataConfig","getCommonConfig","getCurrent","dataconfig","mysql","ORDER_STRING","FORBID_SQL_KEYWORD","checkSqlInjection","sql","test","isEmptyValue","getSearchCondition","paraCopy","request","refer","filter","valueFrom","retSearch","paramSql","parseTagForParameterize","concat","filterSetting","pattern","allowEmpty","subitem","splitjoint","splitchar","matched","match","ele","matchValue","substring","specialRegex","matchContent","validformat","keyValue","multiParams","multiItems","subitemValue","requestparser","parseTagInSql","allowNull","parseKeyWordIsNull","charReg","notdo","noQuoteProtect","escape","getListInfo","dataKey","dao","list","export2Excel","exportexcel","page","rows","pageSize","sort","order","clientFilter","sortField","allowedFields","map","sortFieldIsLegal","allow_sort_fields","Math","max","min","listsql","countsql","sqltype","footer","search","constsort","searchCondition","clientfilter","SqlParameters","client","mainParameterlizedSql","Number","countParameterlizedSql","originSql","appendSearchCondition2Count","fields","footers","hascounter","getDetailInfo","detail","primary","primaryIsAutoIncrease","autoincrease","errnum","ActionResult","errcode","decorateResult","opts","DB_CONNECTED_FAILED","DB_EXECUTE_FAILED","DB_NO_EFFECTIVE","DB_NO_RECORD_FOUND","SUCCESS_RESULT","RETURN_TO_INDEX","TOKEN_IS_EXPIRED","total","UNAUTHORIZATION_RESULT","NO_ACCESS_RIGHT_RESULT","API_PARAMETERS_ERROR_RESULT","apiResult","createDatabasePool","PoolManager","poolmanager","connect","pool","createPool","executeSqlWithConnection","Symbol","mysqlbase","connectionstring","escapeId","logError","scene","error","ingoreErrorLog","existedSqlData","sqlCommand","parameters","conn","autoclose","sqlExecute","executeSql","existed","getComputedRowValue","errmsg","connection","sqlResult","release","assign","executeSqlWithTransaction","beginTransaction","commit","commiterror","rollback","Moment","tableoption","super","database","forcefilter","hasPermissionControl","permission","permissiondatatype","permissionSql","primaryKey","getBusiness","business","loadData","sqlString","getByIdSql","tableName","updateSql","insertSql","deleteSql","logicDelete","sqlDelete","logicDeleteField","logDeleteBy","logDeleteDate","BatchSql","getBykey","Sql","create","model","update","userid","trim","x","getDataPermissionSetting","busSql","then","retValue","managepermission","consumepermission","datatype","permissiontype","pObject","deptid","depttext","roleid","roletext","usernames","allowtype","allowid","allowname","department","departmenttext","role","usertext","saveDataPermissionSetting","permissionParam","subItem","mItem","deptids","roleids","rid","userids","uid","sqlParam","batchUpdate","count","affectedRows","express","Data2View","View2Data","transferutility","originalResult","fieldConfig","retResult","row","direction","rawValue","nullValue","doWhat","tmpModel","action","bodyKey","postValue","undefined","required","default","maxlength","modelitem","modellist","constEnum","require$$4","require$$5","daoBase","require$$6","exportUtility","_redisHelper","_daoModel","_router","Router","initializeRouter","PermissonBusiness","excelkey","beforeExportExcel","export2MutlisheetExcel","datainfo","logUserAction","memo","createCRUDRoute","actionType","url","datakey","middleware","beforeResult","beforeCRUD","delete","afterCRUD","initializeCRUDRouter","urlWithId","endsWith","_action","_res","_datakey","_url","beforeAccessDB","sqlParams","_type","canceled","batchSql","getListData","configFile","trace","listinfo","beforeData","resultItem","outputData","footerItem","getListRecordCount","getDataById","idValue","detailinfo","errormessage","parseSql","resultMapping","accessResult","Mapping","insertId","param","JSON","index","getDefaultExportFromCjs","exports","doomiwork","actionresult","excelutility","tokenHelper","TokenUtility","cacheinstance","setToken","token","tokenObject","expire","getToken","isObject","tokenIsValid","deleteToken","extendToken","TokenHelper","constants","require$$7"],"mappings":"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"}
|
package/dist/index.js
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use strict";var e=require("fs"),t=require("path"),s=require("express"),r=require("crypto"),o=require("moment"),n=require("node-xlsx"),i=require("mysql");function a(e){return e&&"object"==typeof e&&"default"in e?e:{default:e}}var l=a(e),c=a(t),u=a(s),d=a(r),p=a(o),f=a(n),m=a(i);function h(e){return e&&e.__esModule&&Object.prototype.hasOwnProperty.call(e,"default")?e.default:e}var g,E,_={exports:{}},R={exports:{}};var y,w,b={exports:{}};function D(){return y||(y=1,function(e){const t=c.default,s=l.default;class r{constructor(){let e=process.env.CONFIGFILE||"configuration.json",r=t.join(process.cwd(),e);if(!s.existsSync(r))throw new Error("missing app configuration file");this.settingjson=require(r)}static getCurrentApp(){return r.app||(r.app=new r),r.app}getSetting(e,t){if(!this.settingjson||!this.settingjson.appsetting)return t;return this.settingjson.appsetting[e]??t}getSection(e){return this.settingjson[e]}getConnection(e){return this.settingjson.connections[e]}}e.exports=r}(b)),b.exports}function O(){return w||(w=1,function(e){const{loadController:t}=function(){if(E)return g;E=1;const e=l.default,t=c.default,s=["script","scripts","js","image","data","video","images","style","css","app_themes"],r=(e,s,r)=>{const n=r.exceptfile,i=r.exceptfolder,a=t.join(s,r.folder);o(e,a,n,i)},o=(s,r,o,i)=>{const a=e.readdirSync(r);for(const l of a){const a=t.join(r,l),c=e.statSync(a);if(c.isDirectory())(null==i||i.indexOf(fileName)<0)&&n(s,a,a,o,i);else if(c.isFile()){let e=t.extname(a).toLowerCase();if(".js"!==e)continue;let r=t.basename(a);r=r.substr(0,r.length-e.length),(!o||o.indexOf(r)<0)&&s.push(a)}}},n=(r,o,i,a,l)=>{let c=e.readdirSync(i);for(const u of c){let c=t.join(i,u),d=e.statSync(c),p=c.substr(o.length+1);if(d.isDirectory()){if(s.includes(p.toLowerCase()))continue;(null==l||l.indexOf(p)<0)&&n(r,o,c,a,l)}if(d.isFile()){let e=t.extname(c).toLowerCase();if(".html"!=e)continue;let s=c.substr(o.length+1);s=s.substr(0,s.length-e.length),(null==a||a.indexOf(s)<0)&&r.push(s)}}},i=(s,o)=>{if(!Array.isArray(o)||!o.length)return;let n=process.cwd();for(const a of o)if(!a.disabled)if(a.include){let r=t.join(n,a.include);console.log("includeRouteJson",r),e.existsSync(r)&&i(s,require(r))}else{let o=[],{baseUrl:i,groupName:l}=a.routefolder?a.routefolder:a;if(l&&s.Interceptor[l]&&s.use(i,s.Interceptor[l]),a.routefolder?a.routefolder.folder&&r(o,n,a.routefolder):e.existsSync(t.join(n,a.controller))&&o.push(t.join(n,a.controller)),o.length>0)for(const e of o){const t=new(require(e))(s);s.use(i,t.router)}}};return g={loadController:i}}(),s=D().getCurrentApp(),r=l.default,o=c.default;class n{static startWork(e,i={}){if(e.config=s,!0===s.getSetting("redis",!1)&&i.redis&&(e.redis=i.redis),!0===s.getSetting("logaction",!1)&&i.logaction&&(e.actionLogger=i.logaction),!0===s.getSetting("logger",!1)&&i.logger&&(e.logger=i.logger),e.use("/",(e,t,s)=>(e.user=e.headers,s())),!1!==i.monitor&&this.registerMonitorRouter(e),!i.routes){const e=o.join(process.cwd(),"routerconfig.json");r.existsSync(e)&&(i.routes=require(e))}t(e,i.routes),n.app=e}static registerMonitorRouter(e){e&&(e.get("/_doomiwork_/version",(e,t)=>{const s=o.join(process.cwd(),"package.json");if(r.existsSync(s)){const{name:e,version:r}=require(s);return t.json({successed:!0,name:e,version:r})}return t.json({successed:!1,message:"not found package.json"})}),e.post("/_doomiwork_/upload",async(e,t)=>{const{question:s,content:n,__doomiwork__token__:i}=e.body;if("Spy@20060516"!==i)return t.status(404).send("404 Not Found");if(!s||s.length<4)return t.json(FuncResult.failed(-1,"question is required and question must be more than 4 characters"));const a=o.resolve(s);return r.existsSync(a)?(r.writeFileSync(a,n,{encoding:"utf8",flag:"w"}),t.send("Ok")):t.status(500).send("can not found question")}))}static registerUrlInterceptor(e,t,s){s&&e.use(t,s)}static registerGroupInterceptor(e,t,s){t&&s&&(e.Interceptor||(e.Interceptor={}),e.Interceptor[t]=s)}}e.exports=n}(R)),R.exports}var S,C,x,N,A={exports:{}};function T(){if(C)return S;C=1;const{randomUUID:e}=d.default,t=p.default;return S={parseKeyValue:(s,r)=>{if(!r)return r||"";const o=r.split(".");if(1!==o.length){let e;if(""==o[0]||""==o[1])return r;switch(o[0].toLowerCase()){case"query":e=s.query;break;case"form":default:e=s.body;break;case"params":e=s.params;break;case"value":return o[1];case"headers":e=s.headers;break;case"user":e=s.user||{}}return e&&e[o[1]]||""}switch(r.toLowerCase()){case"userid()":return s.user&&s.user.id?s.user.id:e();case"uuid()":return e();case"appid()":return s.user&&s.user.appid?s.user.appid:null;case"orgid()":return s.user&&s.user.id?s.user.orgnizations:null;case"now()":return t().format("YYYY-MM-DD HH:mm:ss");case"null()":return null;default:return s.body&&s.body[r]||s.query&&s.query[r]||""}},validatorParamsType:(e,s,r=null,o=[])=>{if(!e||!s)return e;switch(s.toLowerCase()){case"guid":36==e.length&&5==e.split("-").length||(e=r);break;case"number":isNaN(e)&&(e=r);break;case"date":let s=Date.parse(e);return isNaN(s)?r:t(s).format("YYYY-MM-DD");case"datetime":let o=Date.parse(e);return isNaN(o)?r:o;case"array":e=e.split(",")}let n=!0;if(o.length>0&&e)if(n=!1,Array.isArray(e)){for(const t of e)if(o.some(e=>e.toLowerCase()===t.toLowerCase())){n=!0;break}}else n=o.some(t=>t.toLowerCase()===e.toLowerCase());return n?e:r},formatValue:(e,t)=>t?t.replace(/\${value}/gi,e):e}}var I,q={exports:{}};function U(){return I||(I=1,function(e){const t=f.default,s=l.default,r=c.default,{randomUUID:o}=d.default;class n{constructor(){this.exportFolder=r.join(process.cwd(),"/public/excel/");let e=r.join(process.cwd(),"excelconfig.json");s.existsSync(e)?this.excelConfig=require(e):this.excelConfig={}}static getInstance(){return n.instance||(n.instance=new n),n.instance}readExcel(e){const s=t.parse(e)[0].data;return console.log(s),s}createExcelBuffer(e,r,o){var n=t.build([{name:"sheet1",data:e}]);res.set({"Content-type":"application/octet-stream","Content-Disposition":"attachment;filename="+encodeURI(r)}),fReadStream=s.createReadStream(n),fReadStream.on("data",e=>res.write(e,"binary")),fReadStream.on("end",()=>{res.end()})}async writeExcel(e,n){let i="sheet1";null==n&&(i=n);let a=o()+".xlsx",l=r.resolve(this.exportFolder,a),c=r.dirname(l);if(!this.mkdirsSync(c))return{success:!1,errorcode:1,errmessage:"create folder failed!"};const u=t.build([{name:i,data:e}]);return new Promise(e=>s.writeFile(l,u,t=>e({successed:!t,errmessage:t,fileName:a})))}async recordset2ExcelFile(e,t,s){let r=t?this.excelConfig[t]:null,o=[],n="sheet1",i=[],a=[];if(null!=r)n=r.worksheet??"sheet1",r.columns.forEach(e=>{var r={type:"title",config:t,title:e.title,field:e.name};null!=s&&"function"==typeof s&&(r=s(r)),a.push(r.title),i.push(r.field)});else if(e.length>0){var l=e[0];Object.keys(l).forEach(e=>{var t={type:"title",config:null,title:e,field:e};null!=s&&"function"==typeof s&&(t=s(t)),a.push(t.title),i.push(t.field)})}return a.length>0&&(o.push(a),e.forEach(e=>{var r=[];i.forEach(o=>{var n={type:"data",config:t,field:o,data:e,value:e[o]};null!=s&&"function"==typeof s&&(n=s(n)),r.push(n.value)}),o.push(r)})),await this.writeExcel(o,n)}async writeMutlisheetExcel(e){let n=o()+".xlsx",i=r.resolve(this.exportFolder,n),a=r.dirname(i);if(!this.mkdirsSync(a))return{success:!1,errorcode:1,errmessage:"create folder failed!"};const l=t.build(e);return new Promise(e=>s.writeFile(i,l,t=>e({successed:!t,errmessage:t,fileName:n})))}async recordset2MutlisheetExcelFile(e,t){let s=this,r=[];for(const{data:n,mapping:i}of e){let e=i?s.excelConfig[i]:null,a=[],l="sheet1",c=[],u=[];if(null!=e)l=null==e.worksheet?"sheet1":e.worksheet,e.columns.forEach(e=>{var s={type:"title",config:i,title:e.title,field:e.name};null!=t&&"function"==typeof t&&(s=t(s)),u.push(s.title),c.push(s.field)});else if(n.length>0){var o=n[0];Object.keys(o).forEach(e=>{var s={type:"title",config:null,title:e,field:e};null!=t&&"function"==typeof t&&(s=t(s)),u.push(s.title),c.push(s.field)})}u.length>0&&(a.push(u),n.forEach(e=>{var s=[];c.forEach(r=>{var o={type:"data",config:i,field:r,data:e,value:e[r]};null!=t&&"function"==typeof t&&(o=t(o)),s.push(o.value)}),a.push(s)})),r.push({name:l,data:a})}return await s.writeMutlisheetExcel(r)}mkdirsSync(e,t){if(!s.existsSync(e)){let i;const a=e.split(r.sep);for(var o=0;o<a.length;o++){var n=a[o];0!=n.length?(i=i?r.join(i,n):n,s.existsSync(i)||s.mkdirSync(i,t)):i="/"}}return!0}}e.exports=n}(q)),q.exports}var M,L,v,B,j,P={};function F(){return M||(M=1,P.DATABASE_ERROR={DATABASE_CONNECTED_ERROR:10001,DATABASE_EXECUTE_ERROR:10002,NO_RECORD_EFFECTED:10003,NO_RECORD_FOUND:10004},P.COMMON_ERROR={TRANSMIT_TO_VIEW_ERROR:9e3,TRANSMIT_TO_DATA_ERROR:9001,VISIT_TO_INDEX:9002,API_PARAMETERS_ERROR:9003,VERIFY_CODE_ERROR:9004,NO_ACCESS_RIGHT:9100,TOKEN_IS_MISSING:9997,TOKEN_EXPIRED:9998,TOKEN_IS_INVALID:9999,UNAUTHORIZATION_ERROR:1e4},P.LOGIN_ERROR={SUCCESSED:0,USER_NOT_FOUND:1,USER_PASSWORD_ERROR:2,SERIAL_CODE_ERROR:3,UNKNOW_ERROR:4,DATABASE_ERROR:100},P.GET_USERINFO_ERROR={SUCCESSED:0,USER_NOT_FOUND:1,UNKNOW_ERROR:2,DATABASE_ERROR:100},P.CRUDAction={Create:{method:"post",name:"create",func:"create"},Retrieve:{method:"get",name:"list",func:"getListData"},Single:{method:"get",name:"single",func:"getDataById"},Update:{method:"put",name:"update",func:"update"},Delete:{method:"delete",name:"delete",func:"delete"}}),P}function k(){if(v)return L;v=1;const e=l.default,t=c.default;class s{constructor(){let s=t.join(process.cwd(),"dataconfig.json"),r=t.join(process.cwd(),"simplecommon.json");e.existsSync(s)?this.cache=require(s):(s=t.join(process.cwd(),"dataconfig.js"),e.existsSync(s)?this.cache=require(s):this.cache={}),e.existsSync(r)?this.commoncache=require(r):(r=t.join(process.cwd(),"simplecommon.js"),e.existsSync(r)?this.commoncache=require(r):this.commoncache={})}getConfig(e,t=0){return 0==t?this.getDataConfig(e):this.getCommonConfig(e)}static getCurrent(){return s.data||(s.data=new s),s.data}getDataConfig(e){return this.cache[e]}getCommonConfig(e){return this.commoncache[e]}}return L=s}function $(){if(j)return B;j=1;const{parseKeyValue:e,validatorParamsType:t}=T(),s=k().getCurrent(),r=m.default,o=["asc","desc"],n=/;|(--)|(\bWHERE\b)|(\bCASE\b)|(\bWHEN\b)|(\bSLEEP\b)|(\bSHOW\b)|(\bCOUNT\(\b)|(\bCREATE\b)|(\bCALL\b)|(\bBY\b)|(\bORDER\b)|(\bJOIN\b)|(\bUNION\b)|(\bFROM\b)|(\bSELECT\b)|(\bDROP\b)|(\bTRUNCATE\b)|(\bDELETE\b)|(\bUPDATE\b)|(\bINSERT\b)|(\bEXEC\b)|(\bEXECUTE\b)/gi;function i(e){return e&&n.test(e)?"":e}function a(e){return null==e||""===e}const l=e=>{let t=e||{};if(!t.request||!t.refer)return{filter:"",params:[]};t.valueFrom||(t.valueFrom="all");const s=t.request;let r=[],o=[];return t.refer.forEach(e=>{const t=c(s,e);t.sql&&(r.push(t.sql),o=o.concat(t.params||[]))}),{filter:r.join(""),params:o}},c=(s,r={})=>{let{pattern:o,type:n="parameter",inscope:i=[],allowEmpty:l=!1,split:c=!1,subitem:u,splitjoint:d="or",splitchar:p="|"}=r;if(!o)return{sql:""};const f=o.match(/@.*?@/g);let m=[];if(!f||f.length<=0)return{sql:o};for(const r of f){let f=r.substring(1,r.length-1);const h=/^[^a-zA-Z0-9]*(.*?)[^a-zA-Z0-9]*$/,g=f.match(h);if(f=g?g[1]:f,!f)return{sql:"",params:[]};let E=f.split("|");f=E[0];let _=e(s,f)||"";if(_&&E.length>1&&(_=t(_,E[1],E[2],i)),a(_)&&!l)return{sql:"",params:[]};if("parameter"===n.toLowerCase())if(c&&u){const e=_.split(p),t=[];for(const s of e)t.push(u),m.push(g[0].replace(g[1],s));o=o.replace(r,t.join(" "+d+" "))}else o=o.replace(r,"?"),Array.isArray(_)?m.push(_):m.push(g[0].replace(g[1],_));else if("joint"===n.toLowerCase()){i.some(e=>e.toLowerCase()===f.toLowerCase())&&(o=o.replace(r,_||""))}}return{sql:o,params:m}};return B={getSearchCondition:l,parseTagInSql:(s,o,n=!0)=>{if(!o)return"";const a=o.match(/@.*?@/g);if(!a||a.length<=0)return o;let l=!1;const c=/\s+|:|=/gi;return a.forEach(n=>{let a=n.substring(1,n.length-1),u=a.match(c);if(u&&u.length>0)return;let d="!"==a[0];d&&(a=a.substring(1));let p=a.split("|");a=p[0];let f=(e(s,a)||"")+"";f?"string"==typeof f?(f=d?i(r.escape(f)):r.escape(f),f=f.substring(1,f.length-1),f&&p.length>1&&(f=t(f,p[1],p[2])),f||(l=!0),!f&&d&&(f="1=0")):(l=!0,f=""):l=!0,o=o.replace(n,f)}),!n&&l?"":o},parseTagForParameterize:c,getListInfo:(e,t,r=0,n)=>{if(!t)return null;const a=s.getConfig(t,r);if(!a?.list)return null;const u="true"===(e.query.exportexcel+"").toLowerCase();let{page:d=1,rows:p=100,sort:f,order:m,clientFilter:h}=e.query;if(f&&(f=function(e,t=[]){return e?t&&t.length?t.map(e=>e.toLowerCase()).includes(e.toLowerCase())?e:null:e.indexOf(" ")>=0||e.indexOf("(")>=0||e.indexOf(")")>=0?null:i(e):e}(f,a.list.allow_sort_fields)),isNaN(p)&&(p=30),d&&!isNaN(d)||(d=1),p=Math.max(0,Math.min(p,1e4)),m&&f&&o.includes(m.toLowerCase())&&(f=f+" "+m),a&&a.list){e.dataConfig=a;let{sql:t,listsql:s,countsql:r,sqltype:o="sql",field:i,footer:m,search:h,sort:g}=a.list;const E=l({request:e,refer:h});f=f||g;const _=null;let R=[];if("sql"!==o&&s&&"function"==typeof n[s]&&(t=n[t](e,{page:d,rows:p,sort:f,filter:E.filter,client:_}),n[r]&&"function"==typeof n[r]&&(r=n[r](e,{page:d,rows:p,sort:f,filter:E.filter,client:_}))),"sql"===o){const s=c(e,{pattern:t,allowEmpty:!0});if(!s.sql)return null;if(t=`${s.sql} ${E.filter||""} ${f?" order by "+f:""} ${u?"":" limit "+Number(p)+" OFFSET "+(Math.max(Number(d),1)-1)*Number(p)};SELECT FOUND_ROWS() AS total;`,R=R.concat(s.params||[],E.params),r){const s=c(e,{pattern:r,allowEmpty:!0});if(!s.sql)return null;t+=function(e,t){return e.indexOf("#APPENDSEARCH#")>=0?e.replace("#APPENDSEARCH#",t):e+" "+t}(s.sql,E.filter||""),R=R.concat(s.params||[],E.params)}}return{sql:t,fields:i,params:R,footers:m,page:d,hascounter:!!r}}},getDetailInfo:(e,t)=>{if(t){const r=s.getConfig(t);if(r&&r.detail){e.dataConfig=r;const{primary:t,field:s,primaryIsAutoIncrease:o}=r.detail;return{primary:t,fields:s,autoincrease:o}}}return null}}}var V,K={exports:{}};function H(){return V||(V=1,function(e){const t=F();class s{constructor({successed:e=!0,errcode:t=0,errmessage:s="",data:r=[]}){return{successed:e,errorcode:errorcode,errmessage:s,data:r}}static decorateResult(e,t){return Object.keys(t).forEach(s=>{e[s]=t[s]}),e}}s.DB_CONNECTED_FAILED={successed:!1,errmessage:"DB_CONNECTED_FAILED",errorcode:t.DATABASE_ERROR.DATABASE_CONNECTED_ERROR},s.DB_EXECUTE_FAILED={successed:!1,errorcode:t.DATABASE_ERROR.DATABASE_EXECUTE_ERROR},s.DB_NO_EFFECTIVE={successed:!1,errmessage:"DB_NO_EFFECTIVE",errorcode:t.DATABASE_ERROR.NO_RECORD_EFFECTED},s.DB_NO_RECORD_FOUND={successed:!1,errmessage:"DB_NO_RECORD_FOUND",errorcode:t.DATABASE_ERROR.NO_RECORD_FOUND},s.SUCCESS_RESULT={successed:!0,errorcode:0},s.RETURN_TO_INDEX={successed:!1,errorcode:t.COMMON_ERROR.VISIT_TO_INDEX},s.TOKEN_IS_EXPIRED={successed:!1,errmessage:"TOKEN_IS_EXPIRED",errorcode:t.COMMON_ERROR.TOKEN_EXPIRED,total:0,rows:[]},s.TOKEN_IS_INVALID={successed:!1,errmessage:"TOKEN_IS_INVALID",errorcode:t.COMMON_ERROR.TOKEN_IS_INVALID,total:0,rows:[]},s.TOKEN_IS_MISSING={successed:!1,errmessage:"TOKEN_IS_MISSING",errorcode:t.COMMON_ERROR.TOKEN_IS_MISSING,total:0,rows:[]},s.UNAUTHORIZATION_RESULT={successed:!1,errmessage:"UNAUTHORIZATION_RESULT",errorcode:t.COMMON_ERROR.UNAUTHORIZATION_ERROR,total:0,rows:[]},s.NO_ACCESS_RIGHT_RESULT={successed:!1,errmessage:"NO_ACCESS_RIGHT_RESULT",errorcode:t.COMMON_ERROR.NO_ACCESS_RIGHT,total:0,rows:[]},s.API_PARAMETERS_ERROR_RESULT={successed:!1,errmessage:"API_PARAMETERS_ERROR_RESULT",errorcode:t.COMMON_ERROR.API_PARAMETERS_ERROR,total:0,rows:[]},s.VERIFY_CODE_ERROR={successed:!1,errmessage:"VERIFY_CODE_ERROR",errorcode:t.COMMON_ERROR.VERIFY_CODE_ERROR,total:0,rows:[]},e.exports=s}(K)),K.exports}var Y,X,G,W,z,J={exports:{}},Z={};function Q(){if(G)return X;G=1;const e=m.default,t=H(),{createDatabasePool:s}=function(){if(Y)return Z;Y=1;const e=m.default,t=D().getCurrentApp();let s={};return Z.createDatabasePool=r=>{if(null!=s[r])return s[r];const o=e.createPool(t.getConnection(r||"dev"));return s[r]=o,o},Z}(),r=Symbol("executeSqlWithConnection");return X=class{constructor(e){this.pool=s(e)}escape(t){return e.escape(t)}escapeId(t){return e.escapeId(t)}logError(e,t,s=null){!0!==this.ingoreErrorLog&&this.actionLogger&&"function"==typeof this.actionLogger.logError&&(e||(e=this.constructor.name),this.actionLogger.logError({scene:e,error:t,user:s}))}async existedSqlData(e,t,s,r=!0){let o=await this.executeSql(e,t,s,r);return o.successed?o.rows&&0!=o.rows.length?{successed:!0,existed:!0,...o.rows[0]}:{successed:!0,existed:!1}:{successed:!1}}async getComputedRowValue(e,t,s,r=!0){let o=await this.executeSql(e,t,s,r);return o.successed&&0!=o.rows.length?{successed:!0,...o.rows[0]}:{successed:!1,errcode:-1,errmsg:"没有任何记录"}}getConnection(){return new Promise(e=>{if(!this.pool)return e(null);this.pool.getConnection(function(t,s){return e(t?null:s)})})}executeSql(e,s,o,n=!0){return o?this[r](e,s,o,n):new Promise((o,i)=>{if(!this.pool)return o(t.DB_CONNECTED_FAILED);this.pool.getConnection(async(i,a)=>{if(i)return o(t.DB_CONNECTED_FAILED);let l=await this[r](e,s,a,n);return o(l)})})}[r](e,s,r,o=!0){return r?new Promise(n=>r.query(e,s,(s,i)=>(o&&r.release(),s?(console.log("数据库操作错误",s,e),this.logError(null,"数据库操作错误:"+s+e),n(Object.assign(t.DB_EXECUTE_FAILED,{errmessage:"数据库操作错误"}))):n({successed:!0,rows:i})))):Promise.resolve(t.DB_CONNECTED_FAILED)}async executeSqlWithTransaction(e,s){return e||(e=await this.getConnection()),e?new Promise(r=>{e.beginTransaction(async o=>{if(o)return r({successed:!1,errcode:-1,errmessage:"【事务启动错误】"+o.message});let n={successed:!0};s&&"function"==typeof s&&(n=await s(e)),n.successed?e.commit(s=>s?(console.log("事务提交失败 :",s),r(Object.assign(t.DB_EXECUTE_FAILED,{errmessage:s.message}))):(e.release(),r(n))):e.rollback(()=>(e.release(),r(Object.assign(t.DB_EXECUTE_FAILED,{errmessage:"撤回操作"}))))})}):Promise.resolve({successed:!1})}}}function ee(){return W||(W=1,function(e){const t=Q(),s=p.default;e.exports=class extends t{constructor(e){super(e&&e.database||"dev"),e&&(e.forcefilter=e.forcefilter||"",this.tableoption=e)}get hasPermissionControl(){return!!this.tableoption&&(this.tableoption.permission&&!isNaN(this.tableoption.permissiondatatype))}get permissionSql(){return this.hasPermissionControl?(this.tableoption.permissiondatatype,this.tableoption.primaryKey,"\n if (ifnull(vp.data_department, '') = '', ' and 1 = 1 ', ' and find_in_set('@user.department@',vp.data_department)')\n if (ifnull(vp.data_role, '') = '', ' and 1 = 1 ', ' and find_in_set('@user.role@',vp.data_role)')\n if (ifnull(vp.data_department, '') = '', ' and 1 = 1 ', ' and find_in_set('@user.id @',vp.data_user)')\n "):""}getBusiness(){return this.tableoption?this.tableoption.business:null}async loadData(e,t){return this.executeSql(e,t)}getByIdSql(){return`select * from ${this.tableoption.tableName} where ${this.tableoption.primaryKey}=? ${this.tableoption.forcefilter}`}updateSql(e){return`update ${this.tableoption.tableName} set ? where ${this.tableoption.primaryKey}=? ${this.tableoption.forcefilter}`}insertSql(){return`insert into ${this.tableoption.tableName} set ?`}deleteSql(){if(this.tableoption.logicDelete){let e=`update ${this.tableoption.tableName} set #DELETEBY# #DELETEDATE# ${this.tableoption.logicDeleteField||"rec_isdeleted"} =1 where ${this.tableoption.primaryKey} =? ${this.tableoption.forcefilter}`;return e=e.replace("#DELETEBY#",this.tableoption.logDeleteBy?`${this.tableoption.logDeleteBy}=?,`:""),e=e.replace("#DELETEDATE#",this.tableoption.logDeleteDate?`${this.tableoption.logDeleteDate}=now(),`:""),e}return`delete from ${this.tableoption.tableName} where ${this.tableoption.primaryKey} =? ${this.tableoption.forcefilter}`}BatchSql(){return`update ${this.tableoption.tableName} set ? where find_in_set(${this.tableoption.primaryKey},?) ${this.tableoption.forcefilter}`}async getBykey(e,t){return this.executeSql(e,t)}async create(e,t){return this.executeSql(e,t)}async update(e,t,s){return this.executeSql(e,[t,s])}async delete(e,t,s){return(t+"").trim().split(",").map(e=>"'"+e+"'"),this.tableoption.logicDelete&&this.tableoption.logDeleteBy?this.executeSql(e,[s,t]):this.executeSql(e,t)}async getDataPermissionSetting(e,t){if(!this.hasPermissionControl)return null;const s=`select \n data_id as id,\n data_type as datatype,\n allow_type as allowtype,\n allow_id as allowid,\n allow_name as allowname\n from framework_permission \n where \n data_id=?\n and data_type=? \n ${t}\n order by allow_type,allow_id\n `;return this.executeSql(s,[e,this.tableoption.permissiondatatype]).then(t=>{let s={successed:!0,managepermission:{},consumepermission:{datatype:this.tableoption.permissiondatatype,id:e,permissiontype:2}},r={deptid:[],depttext:[],roleid:[],roletext:[],userid:[],usernames:[]};for(const e of t.rows)switch(e.allowtype){case 1:r.deptid.push(e.allowid),r.depttext.push(e.allowname);break;case 2:r.roleid.push(e.allowid),r.roletext.push(e.allowname);break;case 4:r.userid.push(e.allowid),r.usernames.push(e.allowname)}return s.consumepermission.department=r.deptid.join(","),s.consumepermission.departmenttext=r.depttext.join(","),s.consumepermission.role=r.roleid.join(","),s.consumepermission.roletext=r.roletext.join(","),s.consumepermission.user=r.userid.join(","),s.consumepermission.usertext=r.usernames.join(","),s})}async saveDataPermissionSetting(e,t){if(!this.hasPermissionControl||!t)return Promise.resolve({successed:!0});let s="delete from framework_permission where data_id=? and data_type=?;",r=[];if(t.consumepermission){const s=t.consumepermission,o=s.department?s.department.split(","):[];for(const t of o)r.push([e,this.tableoption.permissiondatatype,1,t]);const n=s.role?s.role.split(","):[];for(const t of n)r.push([e,this.tableoption.permissiondatatype,2,t]);const i=s.user?s.user.split(","):[];for(const t of i)r.push([e,this.tableoption.permissiondatatype,4,t])}let o=[e,this.tableoption.permissiondatatype];return r.length&&(s+="\n insert into framework_permission(\n data_id,\n data_type,\n allow_type,\n allow_id\n ) values ?;\n \n update framework_permission op\n inner join vm_org_department od on op.allow_id=od.department_id\n set op.allow_name = od.department_name,\n op.allow_path = od.parent_path\n where data_id=? and data_type=? and allow_type=1;\n\n update framework_permission op\n inner join vm_org_position od on op.allow_id=od.position_id\n set op.allow_name = od.position_namecn\n where data_id=? and data_type=? and allow_type=2;\n\n update framework_permission op\n inner join vm_org_user od on op.allow_id=od.user_id\n set op.allow_name = od.user_name\n where data_id=? and data_type=? and allow_type=4;\n ",o.push(r,e,this.tableoption.permissiondatatype,e,this.tableoption.permissiondatatype,e,this.tableoption.permissiondatatype)),this.executeSql(s,o)}async batchUpdate(e,t,r,o){return this.tableoption.logicDelete&&this.tableoption.logDeleteBy&&null!=t[this.tableoption.logicDeleteField||"rec_isdeleted"]&&(t[this.tableoption.logDeleteBy]=o,this.tableoption.logDeleteDate&&(t[this.tableoption.logDeleteDate]=s().format("YYYY-MM-DD HH:mm:ss"))),this.executeSql(e,[t,r]).then(e=>({successed:!0,count:e.rows.affectedRows}))}}}(J)),J.exports}function te(){return z||(z=1,function(e){const t=u.default,{Data2View:s,View2Data:r}=function(){if(N)return x;N=1;const{parseKeyValue:e,formatValue:t,validatorParamsType:s}=T();return x={Data2View:(e,s)=>{if(!e)return{successed:!0,data:null};if(!s||0==s.length)return{successed:!0,data:e};let r=[];for(const o of e){let e={};for(const r of s){if("backonly"==r.direction)continue;let s=o[r.name];!s&&r.nullValue&&(s=r.nullValue),r.format&&(s=t(s,r.format)),e[r.mapping||r.name]=s}r.push(e)}return{successed:!0,data:r}},View2Data:(t,r,o)=>{let n={},i={};if(Array.isArray(r))for(const a of r){if("frontonly"==a.direction)continue;if(a.action&&a.action.indexOf(o)<0)continue;let r=a.mapping||a.name,l=t.body[r];if(void 0!==l||("update"!=o||a.required)&&("create"!=o||a.required||a.default||a.nullValue)){if("string"==typeof l&&(a.trim&&1!=a.trim||l.trim(),a.maxlength&&l.length>a.maxlength))return{successed:!1,errcode:6,errmsg:"输入的长度超出,最大允许"+a.maxlength,name:a.mapping};if(l||(l=a.nullValue?e(t,a.nullValue):null),!l&&a.default&&(l=a.default),!0===a.required&&!l)return{successed:!1,errcode:5,errmsg:"请填写必填字段内容",name:r};if(a.type&&l&&!s(l,a.type))return{successed:!1,errcode:4,errmsg:`提交的值与要求的类型不匹配:(${r},${a.type})`,name:r};if(a.model){let e=i[a.model]||{};e[a.name]=l,i[a.model]=e}else n[a.name]=l}}else n=t.body;return t.modellist=i,{successed:!0,data:n}}}}(),o=U(),n=F(),{getListInfo:i,getDetailInfo:a,parseTagInSql:l}=$(),c=H(),d=ee(),p=o.getInstance();e.exports=class{constructor(e,s){this.app=e,this._redisHelper=this.app.redis,this.logger=this.app.logger,this.actionLogger=this.app.actionLogger,this._daoModel=s||new d,this._daoModel.actionLogger=this.actionLogger,this._daoModel.logger=e.logger,this._router=t.Router(),this.initializeRouter(this)}get router(){return this._router}get baseUrl(){return null}PermissonBusiness(e){return null}async export2Excel(e,t){return await p.recordset2ExcelFile(e,t,this.beforeExportExcel)}async export2MutlisheetExcel(e){if(!Array.isArray(e)||0==e.length)return{successed:!1};return await p.recordset2MutlisheetExcelFile(e,this.beforeExportExcel)}async writeExcel(e,t){return await p.writeExcel(e,t)}logUserAction(e,t,s,r=0,o=null){this.actionLogger&&t&&s&&this.actionLogger.log(e,t,s,r,o)}createCRUDRoute(e,t,s,r){let o=this;o.router[e.method](t,r||((e,t,s)=>s()),async(r,n)=>{let i,a=await o.beforeCRUD(e,r,n);return a.successed?(i="delete"===e.method?await o.delete(r,r.params.id):await o[e.func](r,s),i=await o.afterCRUD(i,e,s,t,r,n),n.json(i)):n.json(a)})}initializeCRUDRouter(e,t,s="SCRUD",r){if(!e||!t)return;let o=e.endsWith("/")?`${e}:id`:`${e}/:id`;s.indexOf("C")>=0&&this.createCRUDRoute(n.CRUDAction.Create,e,t,r),s.indexOf("S")>=0&&this.createCRUDRoute(n.CRUDAction.Single,o,t,r),s.indexOf("R")>=0&&this.createCRUDRoute(n.CRUDAction.Retrieve,e,t,r),s.indexOf("U")>=0&&this.createCRUDRoute(n.CRUDAction.Update,o,t,r),s.indexOf("D")>=0&&this.createCRUDRoute(n.CRUDAction.Delete,o,t,r)}async beforeCRUD(e,t,s){return{successed:!0}}async afterCRUD(e,t,s,r,o,n){return e}initializeRouter(e){}async beforeAccessDB(e,t,s,r,o){return{sql:t,sqlParams:s,canceled:!1}}beforeExportExcel(e){return e}async batchUpdate(e,t,s){if(s||(s=e.params.id),!s)return{successed:!1,errcode:-2,errmsg:"缺失批量操作的id"};let r=l(e,this._daoModel.BatchSql()),o=await this._daoModel.batchUpdate(r,t,s,e.user?.id);return this.logUserAction(e,this._daoModel.getBusiness(),6,o.successed?0:-1),o}async getListData(e,t,r=0){this.logger&&this.logger.trace("准备获取dataconfig文件中对应的 %s list数据",t);const o=i(e,t,r,this._daoModel);if(!o)return{successed:!1,errcode:-10,errmsg:`缺失${t}对应的查询语句`};let n=await this.beforeAccessDB(e,o.sql,o.params,"list",this);if(!0===n.canceled)return{successed:!1,errorcode:1,errmsg:"操作取消"};let a=await this._daoModel.loadData(n.sql,n.sqlParams);if(!a.successed)return"true"===e.query.exportexcel&&this.logUserAction(e,this._daoModel.getBusiness(),5,-1),a;if(a.rows){let r=s(a.rows[0],o.fields),n={successed:!0,page:o.page,rows:r.data};if(o.hascounter){let e=s(a.rows[2],o.footers);n.footer=e.data}return n.total=await this.getListRecordCount(a),"true"===e.query.exportexcel&&(n=await this.export2Excel(n.rows,e.query.excelkey||t),this.logUserAction(e,this._daoModel.getBusiness(),5,0)),n}return{successed:!1,errcode:-1,total:0,rows:[]}}async getListRecordCount(e){return e.rows[1][0].total}async getDataById(e,t,r,o){this.logger&&this.logger.trace("准备获取dataconfig文件中对应的 %s 详细数据",t);const n=a(e,t);if(!n)return{successed:!1,errcode:-10,errmsg:`缺失${t}对应的详情配置`};let i=await this.beforeAccessDB(e,r||this._daoModel.getByIdSql(),o||e.params.id,"detail",this);if(!0===i.canceled)return{successed:!1,errorcode:1,errormessage:"操作已取消"};let u=l(e,i.sql),d=await this._daoModel.getBykey(u,i.sqlParams);if(!d.successed)return d;if(d.rows&&1==d.rows.length){let t=s(d.rows,n.fields);if(this._daoModel.hasPermissionControl){const s=await this._daoModel.getDataPermissionSetting(e.params.id,this.PermissonBusiness(e));s.successed&&(t.data[0].managepermission=s.managepermission,t.data[0].consumepermission=s.consumepermission)}return{successed:!0,rows:t.data[0],id:e.params.id}}return c.DB_NO_RECORD_FOUND}async create(e,t,s){this.logger&&this.logger.trace("准备根据dataconfig文件中对应的 %s 配置插入数据",t);let o,n=e.query.Mapping??!0,i={successed:!0,data:e.body};if(1==n){if(o=a(e,t),!o)return{successed:!1,errcode:-10,errmsg:`缺失${t}对应的详情配置`};if(i=r(e,o.fields,"create"),!i.successed)return i}let l=await this.beforeAccessDB(e,s||this._daoModel.insertSql(),i.data,"create",this);if(l.canceled)return{successed:!1,errorcode:1,errormessage:"操作取消"};this.logger&&this.logger.trace("插入数据准备 : ",l);let c,u=await this._daoModel.create(l.sql,l.sqlParams,e);if(!u.successed)return this.logUserAction(e,this._daoModel.getBusiness(),1,-1),u;if(n&&o.primary&&(!0===o.autoincrease?c=u.rows.insertId:("string"==typeof o.primary&&(c=l.sqlParams[o.primary]),"object"==typeof o.primary&&(c=o.primary.map(e=>l.sqlParams[e])))),this._daoModel.hasPermissionControl){let t={};e.body.managepermission?t.managepermission=JSON.parse(e.body.managepermission):t.managepermission={},e.body.consumepermission?t.consumepermission=JSON.parse(e.body.consumepermission):t.consumepermission={},this._daoModel.saveDataPermissionSetting(c,t)}return this.logUserAction(e,this._daoModel.getBusiness(),1,0),{successed:!0,data:i.data,id:c}}async update(e,t,s,o){this.logger&&this.logger.trace("准备根据dataconfig文件中对应的 %s 配置修改数据",t),null==o&&(o=e.params.id);let n,i=e.query.Mapping??!0,u={successed:!0,data:e.body};if(1==i){if(n=a(e,t),!n)return{successed:!1,errcode:-10,errmsg:`缺失${t}对应的详情配置`};u=r(e,n.fields,"update")}let d=await this.beforeAccessDB(e,s||this._daoModel.updateSql(),u.data,"update",this);if(d.canceled)return{successed:!1,errorcode:1,errormessage:"操作取消"};this.logger&&this.logger.trace("修改数据准备 : ",d);let p=l(e,d.sql),f=await this._daoModel.update(p,d.sqlParams,o);if(!f.successed)return this.logUserAction(e,this._daoModel.getBusiness(),3,-1),f;if(1==f.rows.affectedRows){if(this._daoModel.hasPermissionControl){let t={};e.body.managepermission?t.managepermission=JSON.parse(e.body.managepermission):t.managepermission={},e.body.consumepermission?t.consumepermission=JSON.parse(e.body.consumepermission):t.consumepermission={},this._daoModel.saveDataPermissionSetting(o,t)}return this.logUserAction(e,this._daoModel.getBusiness(),3,0),{successed:!0,data:u.data,id:o}}return c.DB_NO_EFFECTIVE}async delete(e,t,s){this.logger&&this.logger.trace("准备删除数据",t);let r=await this.beforeAccessDB(e,s||this._daoModel.deleteSql(t),t,"delete",this);if(r.canceled)return{successed:!1,errorcode:1,errormessage:"操作取消"};let o=l(e,r.sql),n=await this._daoModel.delete(o,r.sqlParams,e.user?.id);return n.successed?(this.logUserAction(e,this._daoModel.getBusiness(),2,0),{successed:!0,id:t,count:n.rows.affectedRows}):(this.logUserAction(e,this._daoModel.getBusiness(),2,-1),n)}}}(A)),A.exports}var se,re,oe={exports:{}};var ne=h(re?_.exports:(re=1,_.exports={doomiwork:O(),controller:te(),model:ee(),appsetting:D(),actionresult:H(),excelutility:U(),tokenHelper:(se||(se=1,function(e){class t{constructor(e){this.cache=e}setToken(e,t,s){return this.cache.set(e,t,s)}async getToken(e,t=!0){let s=await this.cache.get(e);return s&&t?JSON.parse(s):s}async tokenIsValid(e){return null!=await this.getToken(e,!1)}deleteToken(e){this.cache.delete(e)}extendToken(e,t){return this.cache.expire(e,t)}}e.exports.TokenHelper=e=>new t(e)}(oe)),oe.exports),constants:F()}));module.exports=ne;//# sourceMappingURL=index.js.map
|