@agile-team/mach-report 2.6.1 → 2.7.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.
Files changed (61) hide show
  1. package/README.md +37 -4
  2. package/dist/ReportPreview-BdvoqdOd.cjs +6 -0
  3. package/dist/ReportPreview-COFkbeEM.js +3719 -0
  4. package/dist/{assets-NVA_sftu.js → assets-B9qJku3V.js} +54 -57
  5. package/dist/assets-RZan7EyL.cjs +1 -0
  6. package/dist/capabilities-joSutDF8.js +63 -0
  7. package/dist/capabilities-xGTpnPjJ.cjs +1 -0
  8. package/dist/designer.cjs +1 -1
  9. package/dist/designer.d.cts +869 -753
  10. package/dist/designer.d.ts +869 -753
  11. package/dist/designer.js +490 -234
  12. package/dist/index.cjs +8 -8
  13. package/dist/index.d.cts +86 -3
  14. package/dist/index.d.ts +86 -3
  15. package/dist/index.js +582 -508
  16. package/dist/pdf.cjs +30 -30
  17. package/dist/pdf.d.cts +11 -3
  18. package/dist/pdf.d.ts +11 -3
  19. package/dist/pdf.js +1501 -1500
  20. package/dist/{plugin-BqBkn_kI.cjs → plugin-9t_ZFwhz.cjs} +1 -1
  21. package/dist/{plugin-Ds10VnQO.js → plugin-s8Ay8kKk.js} +1 -1
  22. package/dist/progress-DD964VAB.js +102 -0
  23. package/dist/progress-KvhwXZ1Q.cjs +1 -0
  24. package/dist/{report-source-B9bENO0F.js → report-source-BXHNy_AD.js} +337 -332
  25. package/dist/report-source-CCAvFE3t.cjs +1 -0
  26. package/dist/server/node.d.cts +26 -3
  27. package/dist/server/node.d.ts +26 -3
  28. package/dist/server-node.cjs +1 -1
  29. package/dist/server-node.js +125 -92
  30. package/dist/server.cjs +1 -1
  31. package/dist/server.d.cts +28 -3
  32. package/dist/server.d.ts +28 -3
  33. package/dist/server.js +172 -164
  34. package/dist/style.css +1 -1
  35. package/dist/task-events-DQ276fn2.cjs +1 -0
  36. package/dist/task-events-Dpsvf_t2.js +47 -0
  37. package/dist/vue/async.d.cts +1507 -2083
  38. package/dist/vue/async.d.ts +1507 -2083
  39. package/dist/vue/index.d.cts +2376 -3310
  40. package/dist/vue/index.d.ts +2376 -3310
  41. package/dist/vue-async.cjs +1 -1
  42. package/dist/vue-async.js +3 -3
  43. package/dist/vue.cjs +1 -1
  44. package/dist/vue.js +131 -107
  45. package/dist/worker.cjs +1 -1
  46. package/dist/worker.d.cts +26 -3
  47. package/dist/worker.d.ts +26 -3
  48. package/dist/worker.js +110 -85
  49. package/dist/xlsx.cjs +14 -14
  50. package/dist/xlsx.d.cts +11 -3
  51. package/dist/xlsx.d.ts +11 -3
  52. package/dist/xlsx.js +656 -652
  53. package/package.json +2 -2
  54. package/dist/ReportPreview-Dk-28QAi.js +0 -2946
  55. package/dist/ReportPreview-FSvcBLjH.cjs +0 -6
  56. package/dist/assets-66UBlhES.cjs +0 -1
  57. package/dist/capabilities-CNjIirfo.js +0 -36
  58. package/dist/capabilities-D4xeVYSR.cjs +0 -1
  59. package/dist/grid-geometry-BNptEcMm.js +0 -65
  60. package/dist/grid-geometry-CZ_cYB6O.cjs +0 -1
  61. package/dist/report-source-BbNkkBDy.cjs +0 -1
package/dist/server.cjs CHANGED
@@ -1 +1 @@
1
- "use strict";var V=Object.create;var q=Object.defineProperty;var z=Object.getOwnPropertyDescriptor;var J=Object.getOwnPropertyNames;var Q=Object.getPrototypeOf,_=Object.prototype.hasOwnProperty;var W=(t,e,a,n)=>{if(e&&typeof e=="object"||typeof e=="function")for(let r of J(e))!_.call(t,r)&&r!==a&&q(t,r,{get:()=>e[r],enumerable:!(n=z(e,r))||n.enumerable});return t};var L=(t,e,a)=>(a=t!=null?V(Q(t)):{},W(e||!t||!t.__esModule?q(a,"default",{value:t,enumerable:!0}):a,t));Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const R=require("./report-source-BbNkkBDy.cjs"),I=require("./report-params-CjWrjPl6.cjs"),C=require("./param-validation-CiTxFeZ8.cjs"),G=require("./validate-DfHPD8wX.cjs");class m extends Error{constructor(e,a,n){super(a),this.code=e,this.path=n,this.name="ReportRuntimeError"}}function x(t){if(!t?.aborted)return;if(t.reason instanceof m)throw t.reason;const e=new Error("报表执行已取消");throw e.name="AbortError",Object.defineProperty(e,"cause",{value:t.reason}),e}function b(t,e,a){if(!Number.isFinite(a)||a<0)throw new m("budget",`${e} 的执行统计无效`,`$.budget.${e}`);const n=t[e];if(n!==void 0&&a>n)throw new m("budget",`${e} 超出预算 ${n}(实际 ${a})`,`$.budget.${e}`)}function U(t){for(const[e,a]of Object.entries(t)){if(a!==void 0&&(!Number.isFinite(a)||a<=0))throw new m("budget",`${e} 应为正有限数字`,`$.budget.${e}`);if(e!=="maxDurationMs"&&a!==void 0&&!Number.isSafeInteger(a))throw new m("budget",`${e} 应为正安全整数`,`$.budget.${e}`);if(e==="maxDurationMs"&&a!==void 0&&a>2147483647)throw new m("budget","maxDurationMs 不能超过 2147483647",`$.budget.${e}`)}}async function B(t,e,a){const n=new AbortController,r=()=>n.abort(t?.reason);t?.addEventListener("abort",r,{once:!0}),t?.aborted&&r();const s=Date.now(),u=e===void 0?void 0:setTimeout(()=>n.abort(new m("timeout",`报表执行超过 ${e}ms`)),e);let o;try{x(n.signal);const i=new Promise((w,f)=>{o=()=>{try{x(n.signal)}catch(v){f(v)}},n.signal.addEventListener("abort",o,{once:!0})}),p=await Promise.race([a(n.signal),i]);if(x(n.signal),e!==void 0&&Date.now()-s>e)throw new m("timeout",`报表执行超过 ${e}ms`);return p}finally{u!==void 0&&clearTimeout(u),o&&n.signal.removeEventListener("abort",o),t?.removeEventListener("abort",r)}}function M(t,e){if(e.length===0)throw new R.ReportSourceError("config","缺少报表 ID");return e.map(a=>{if(!Object.prototype.hasOwnProperty.call(t,a))throw new R.ReportSourceError("config",`未注册报表 ${a}`);return t[a]})}function j(t){return t.grid?.cells.reduce((e,a)=>e+a.reduce((n,r)=>n+(r?1+(r.children?.reduce((s,u)=>s+j(u),0)??0):0),0),0)??0}function X(t,e){return t.pages.reduce((a,n)=>a+n.components.reduce((r,s)=>{if(s.kind!=="list")return r+j(s);const u=e[s.dataset]?.length??0;return r+s.columns.length*(u+(s.headerGrid?.cells.length??1))},0),0)}function H(t,e=Object.keys(t)){return M(t,e).map((a,n)=>{const r=e[n],s=I.getReportParamDefs(t,[r]);return{id:r,params:JSON.parse(JSON.stringify(s)),paramsSchema:C.reportParamsJsonSchema(s),datasetsSchema:Object.fromEntries(Object.entries(a.dataSchema??{}).map(([u,o])=>[u,R.datasetJsonSchema(o)])),capabilities:{save:!!a.provider?.save,export:!!a.provider?.export,templates:!!a.provider?.templates}}})}function A(t,e){M(t,e.reportIds);const a=C.validateReportParams(I.getReportParamDefs(t,e.reportIds),e.params),n=e.reportIds.flatMap(s=>C.validateReportParams(I.getReportParamDefs(t,[s]),e.params).issues),r=new Map(n.map(s=>[JSON.stringify(s),s]));return{...a,ok:r.size===0,issues:[...r.values()]}}function K(t,e){const a=G.validateRenderPlan(t.plan);if(!a.ok)throw new R.ReportSourceError("validate",`执行器返回无效计划:${a.errors[0]?.path}`);const n=t.plan.pages.length,r=t.plan.pages.reduce((s,u)=>s+u.components.reduce((o,i)=>o+j(i),0),0);return b(e,"maxRows",t.stats.rows),b(e,"maxPages",n),b(e,"maxCells",r),{...t,stats:{...t.stats,pages:n,cells:r}}}function N(t,e){const a=A(t.reports,e);if(!a.ok)throw new C.ReportParamValidationError(a.issues)}function F(t=[]){return t.map(({code:e,message:a,severity:n,pageIndex:r,componentIndex:s})=>({code:e,message:a,severity:n,path:`$.pages.${r}.components.${s}`}))}function Y(t){const e={maxRows:1e5,maxPages:1e4,maxCells:2e6,maxOutputBytes:1e8,maxDurationMs:12e4,...t.budget};U(e);const a=async(r,s)=>{const u=Date.now();let o=0,i=0;const p=[],w={},f=Object.fromEntries(Object.entries(t.reports).map(([d,g])=>[d,{...g,pagination:{...t.pagination,...g.pagination,...s?{measurer:s}:{}},dataValidation:{...g.dataValidation,maxRows:Math.min(e.maxRows??1e5,g.dataValidation?.maxRows??1/0),maxCells:Math.min(e.maxCells??2e6,g.dataValidation?.maxCells??1/0)}}])),l=await R.createReportSource(f,{maxPages:e.maxPages,onDatasets:(d,g,P)=>{o+=Object.values(g).reduce(($,S)=>$+S.length,0),b(e,"maxRows",o),i+=X(P,g),b(e,"maxCells",i)}})({...r,params:r.params??{},onWarning:d=>p.push({code:"layout",message:d,severity:"warning"}),onQueryResult:(d,g)=>{Object.defineProperty(w,d,{value:{revision:g.revision,sourceToken:g.sourceToken},enumerable:!0,writable:!0}),p.push(...g.diagnostics??[])}}).catch(d=>{throw d instanceof R.ReportSourceError&&d.cause instanceof R.PaginatePageLimitError?new m("budget",d.cause.message,"$.budget.maxPages"):d});x(r.signal);const c=l.pages.reduce((d,g)=>d+g.components.reduce((P,$)=>P+j($),0),0);return b(e,"maxPages",l.pages.length),b(e,"maxCells",c),{plan:l,diagnostics:p,revisions:w,stats:{rows:o,pages:l.pages.length,cells:c,durationMs:Date.now()-u}}},n=async r=>{const s=Date.now();if(r.format!=="pdf"&&r.format!=="xlsx")throw new R.ReportSourceError("config","不支持的报表导出格式");const u=r.format==="pdf"?await import("@agile-team/mach-report/pdf"):void 0;x(r.signal);const o=r.pdf?.customFontFaces??(r.pdf?.customFontBytes?{regular:r.pdf.customFontBytes}:void 0),i=u&&o?u.createFontBytesMeasurer(o):void 0,p=await a(r,i);x(r.signal);let w;if(r.format==="pdf"){x(r.signal);const l=await u.renderPlanToPdf(p.plan,{...r.pdf,...i?{measurer:i}:{}});w=l.bytes,p.diagnostics.push(...F(l.diagnostics)),p.diagnostics.push(...l.fidelityWarnings.map(c=>({code:"pdf-fidelity",message:c,severity:"warning"})),...l.pageErrors.map(c=>({code:"pdf-page",message:c,severity:"error"}))),l.unsupportedTextCount&&p.diagnostics.push({code:"pdf-font",message:`${l.unsupportedTextCount} 段文本包含当前字体不支持的字符`,severity:"warning"})}else{const{renderPlanToXlsx:l}=await import("@agile-team/mach-report/xlsx");x(r.signal);const c=await l(p.plan,r.xlsx);w=new Uint8Array(c.buffer),p.diagnostics.push(...F(c.diagnostics)),p.diagnostics.push(...c.warnings.map(d=>({code:"xlsx-fidelity",message:d,severity:"warning"})))}x(r.signal),b(e,"maxOutputBytes",w.byteLength);const{plan:f,...v}=p;return{...v,bytes:w,format:r.format,contentType:r.format==="pdf"?"application/pdf":"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet",stats:{...v.stats,durationMs:Date.now()-s,outputBytes:w.byteLength}}};return{describe:r=>H(t.reports,r),validate:r=>A(t.reports,r),prepare:r=>B(r.signal,e.maxDurationMs,async s=>{const{signal:u,...o}=r;N(t,o);const i=t.executor?await t.executor.prepare(o,s):await a({...o,signal:s});return K(i,e)}),export:r=>B(r.signal,e.maxDurationMs,async s=>{const{signal:u,...o}=r;if(N(t,o),o.format!=="pdf"&&o.format!=="xlsx")throw new R.ReportSourceError("config","不支持的报表导出格式");const i=t.executor?await t.executor.export(o,s):await n({...o,signal:s});return b(e,"maxRows",i.stats.rows),b(e,"maxPages",i.stats.pages),b(e,"maxCells",i.stats.cells),b(e,"maxOutputBytes",i.bytes.byteLength),{...i,stats:{...i.stats,outputBytes:i.bytes.byteLength}}})}}function Z(t={}){const e=t.concurrency??1,a=t.maxQueued??20;if(!Number.isSafeInteger(e)||e<1||!Number.isSafeInteger(a)||a<0)throw new m("budget","队列并发应为正整数,排队上限应为非负整数");const n=[],r=new Set,s=new Set;let u=!1,o=0;const i=()=>{for(;!u&&r.size<e&&n.length;)n.shift().start()};return{get active(){return r.size},get pending(){return n.length},enqueue:(w,f={})=>{if(u)throw new m("closed","任务队列已关闭");if(x(f.signal),r.size>=e&&n.length>=a)throw new m("queue-full","报表任务队列已满");const v=f.id??`report-${++o}`;if(s.has(v))throw new m("queue-full","任务 ID 正在执行或排队");const l=new AbortController;let c="queued",d,g,P;const $=new Promise((h,y)=>{g=h,P=y}),S=()=>{f.signal?.removeEventListener("abort",T),s.delete(v)},D=h=>{if(c!=="queued"&&c!=="running")return;const y=c==="queued";c="cancelled",l.abort(h);try{x(l.signal)}catch(O){P(O)}if(y){const O=n.indexOf(E);O>=0&&n.splice(O,1),S(),i()}},T=()=>D(f.signal?.reason),k=(h,y)=>{c==="running"&&(!Number.isFinite(h)||h<0||y!==void 0&&(!Number.isFinite(y)||y<h)||(d={completed:h,...y===void 0?{}:{total:y}}))},E={cancel:D,start:()=>{c==="queued"&&(c="running",r.add(E),Promise.resolve().then(()=>(x(l.signal),w({signal:l.signal,reportProgress:k}))).then(h=>{c==="running"&&(c="completed",g(h))},h=>{c==="running"&&(c="failed",P(h))}).finally(()=>{r.delete(E),S(),i()}))}};return s.add(v),f.signal?.addEventListener("abort",T,{once:!0}),f.signal?.aborted?D(f.signal.reason):r.size<e?E.start():n.push(E),{id:v,get status(){return c},get progress(){return d},result:$,cancel:D}},close:(w={})=>{u=!0;for(const f of[...n])f.cancel(new m("closed","任务队列已关闭"));if(w.cancelRunning)for(const f of r)f.cancel(new m("closed","任务队列已关闭"))}}}exports.ReportRuntimeError=m;exports.createReportRuntime=Y;exports.createReportTaskQueue=Z;
1
+ "use strict";var Q=Object.create;var B=Object.defineProperty;var _=Object.getOwnPropertyDescriptor;var W=Object.getOwnPropertyNames;var G=Object.getPrototypeOf,U=Object.prototype.hasOwnProperty;var X=(r,e,n,a)=>{if(e&&typeof e=="object"||typeof e=="function")for(let t of W(e))!U.call(r,t)&&t!==n&&B(r,t,{get:()=>e[t],enumerable:!(a=_(e,t))||a.enumerable});return r};var N=(r,e,n)=>(n=r!=null?Q(G(r)):{},X(e||!r||!r.__esModule?B(n,"default",{value:r,enumerable:!0}):n,r));Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const P=require("./report-source-CCAvFE3t.cjs"),C=require("./report-params-CjWrjPl6.cjs"),T=require("./param-validation-CiTxFeZ8.cjs"),H=require("./validate-DfHPD8wX.cjs"),$=require("./task-events-DQ276fn2.cjs");class b extends Error{constructor(e,n,a){super(n),this.code=e,this.path=a,this.name="ReportRuntimeError"}}function x(r){if(!r?.aborted)return;if(r.reason instanceof b)throw r.reason;const e=new Error("报表执行已取消");throw e.name="AbortError",Object.defineProperty(e,"cause",{value:r.reason}),e}function y(r,e,n){if(!Number.isFinite(n)||n<0)throw new b("budget",`${e} 的执行统计无效`,`$.budget.${e}`);const a=r[e];if(a!==void 0&&n>a)throw new b("budget",`${e} 超出预算 ${a}(实际 ${n})`,`$.budget.${e}`)}function K(r){for(const[e,n]of Object.entries(r)){if(n!==void 0&&(!Number.isFinite(n)||n<=0))throw new b("budget",`${e} 应为正有限数字`,`$.budget.${e}`);if(e!=="maxDurationMs"&&n!==void 0&&!Number.isSafeInteger(n))throw new b("budget",`${e} 应为正安全整数`,`$.budget.${e}`);if(e==="maxDurationMs"&&n!==void 0&&n>2147483647)throw new b("budget","maxDurationMs 不能超过 2147483647",`$.budget.${e}`)}}async function F(r,e,n){const a=new AbortController,t=()=>a.abort(r?.reason);r?.addEventListener("abort",t,{once:!0}),r?.aborted&&t();const s=Date.now(),d=e===void 0?void 0:setTimeout(()=>a.abort(new b("timeout",`报表执行超过 ${e}ms`)),e);let u;try{x(a.signal);const p=new Promise((w,i)=>{u=()=>{try{x(a.signal)}catch(g){i(g)}},a.signal.addEventListener("abort",u,{once:!0})}),c=await Promise.race([n(a.signal),p]);if(x(a.signal),e!==void 0&&Date.now()-s>e)throw new b("timeout",`报表执行超过 ${e}ms`);return c}finally{d!==void 0&&clearTimeout(d),u&&a.signal.removeEventListener("abort",u),r?.removeEventListener("abort",t)}}function V(r,e){if(e.length===0)throw new P.ReportSourceError("config","缺少报表 ID");return e.map(n=>{if(!Object.prototype.hasOwnProperty.call(r,n))throw new P.ReportSourceError("config",`未注册报表 ${n}`);return r[n]})}function D(r){return r.grid?.cells.reduce((e,n)=>e+n.reduce((a,t)=>a+(t?1+(t.children?.reduce((s,d)=>s+D(d),0)??0):0),0),0)??0}function Y(r,e){return r.pages.reduce((n,a)=>n+a.components.reduce((t,s)=>{if(s.kind!=="list")return t+D(s);const d=e[s.dataset]?.length??0;return t+s.columns.length*(d+(s.headerGrid?.cells.length??1))},0),0)}function Z(r,e=Object.keys(r)){return V(r,e).map((n,a)=>{const t=e[a],s=C.getReportParamDefs(r,[t]);return{id:t,params:JSON.parse(JSON.stringify(s)),paramsSchema:T.reportParamsJsonSchema(s),datasetsSchema:Object.fromEntries(Object.entries(n.dataSchema??{}).map(([d,u])=>[d,P.datasetJsonSchema(u)])),capabilities:{save:!!n.provider?.save,export:!!n.provider?.export,templates:!!n.provider?.templates}}})}function z(r,e){V(r,e.reportIds);const n=T.validateReportParams(C.getReportParamDefs(r,e.reportIds),e.params),a=e.reportIds.flatMap(s=>T.validateReportParams(C.getReportParamDefs(r,[s]),e.params).issues),t=new Map(a.map(s=>[JSON.stringify(s),s]));return{...n,ok:t.size===0,issues:[...t.values()]}}function ee(r,e){const n=H.validateRenderPlan(r.plan);if(!n.ok)throw new P.ReportSourceError("validate",`执行器返回无效计划:${n.errors[0]?.path}`);const a=r.plan.pages.length,t=r.plan.pages.reduce((s,d)=>s+d.components.reduce((u,p)=>u+D(p),0),0);return y(e,"maxRows",r.stats.rows),y(e,"maxPages",a),y(e,"maxCells",t),{...r,stats:{...r.stats,pages:a,cells:t}}}function M(r,e){const n=z(r.reports,e);if(!n.ok)throw new T.ReportParamValidationError(n.issues)}function A(r=[]){return r.map(({code:e,message:n,severity:a,pageIndex:t,componentIndex:s})=>({code:e,message:n,severity:a,path:`$.pages.${t}.components.${s}`}))}function te(r){const e={maxRows:1e5,maxPages:1e4,maxCells:2e6,maxOutputBytes:1e8,maxDurationMs:12e4,...r.budget};K(e);const n=async(t,s)=>{const d=Date.now();let u=0,p=0;const c=[],w={},i=Object.fromEntries(Object.entries(r.reports).map(([l,o])=>[l,{...o,pagination:{...r.pagination,...o.pagination,...s?{measurer:s}:{}},dataValidation:{...o.dataValidation,maxRows:Math.min(e.maxRows??1e5,o.dataValidation?.maxRows??1/0),maxCells:Math.min(e.maxCells??2e6,o.dataValidation?.maxCells??1/0)}}])),m=await P.createReportSource(i,{maxPages:e.maxPages,onDatasets:(l,o,h)=>{u+=Object.values(o).reduce((R,O)=>R+O.length,0),y(e,"maxRows",u),p+=Y(h,o),y(e,"maxCells",p)}})({...t,params:t.params??{},onWarning:l=>c.push({code:"layout",message:l,severity:"warning"}),onQueryResult:(l,o)=>{Object.defineProperty(w,l,{value:{revision:o.revision,sourceToken:o.sourceToken},enumerable:!0,writable:!0}),c.push(...o.diagnostics??[])}}).catch(l=>{throw l instanceof P.ReportSourceError&&l.cause instanceof P.PaginatePageLimitError?new b("budget",l.cause.message,"$.budget.maxPages"):l});x(t.signal);const f=m.pages.reduce((l,o)=>l+o.components.reduce((h,R)=>h+D(R),0),0);return y(e,"maxPages",m.pages.length),y(e,"maxCells",f),{plan:m,diagnostics:c,revisions:w,stats:{rows:u,pages:m.pages.length,cells:f,durationMs:Date.now()-d}}},a=async t=>{const s=Date.now();if(t.format!=="pdf"&&t.format!=="xlsx")throw new P.ReportSourceError("config","不支持的报表导出格式");const d=t.format==="pdf"?await import("@agile-team/mach-report/pdf"):void 0;x(t.signal);const u=t.pdf?.customFontFaces??(t.pdf?.customFontBytes?{regular:t.pdf.customFontBytes}:void 0),p=d&&u?d.createFontBytesMeasurer(u):void 0,c=await n(t,p);x(t.signal);const w=$.createReportTaskReporter(t),i=await w.run("encode",async()=>{let f;if(t.format==="pdf"){x(t.signal);const l=await d.renderPlanToPdf(c.plan,{...t.pdf,...p?{measurer:p}:{},fidelity:t.fidelity,signal:t.signal,onProgress:(o,h)=>w.progress("encode",o,h)});f=l.bytes,c.diagnostics.push(...A(l.diagnostics)),c.diagnostics.push(...l.fidelityWarnings.map(o=>({code:"pdf-fidelity",message:o,severity:"warning"})),...l.pageErrors.map(o=>({code:"pdf-page",message:o,severity:"error"}))),l.unsupportedTextCount&&c.diagnostics.push({code:"pdf-font",message:`${l.unsupportedTextCount} 段文本包含当前字体不支持的字符`,severity:"warning"})}else{const{renderPlanToXlsx:l}=await import("@agile-team/mach-report/xlsx");x(t.signal);const o=await l(c.plan,{...t.xlsx,fidelity:t.fidelity,signal:t.signal,onProgress:(h,R)=>w.progress("encode",h,R)});f=new Uint8Array(o.buffer),c.diagnostics.push(...A(o.diagnostics)),c.diagnostics.push(...o.warnings.map(h=>({code:"xlsx-fidelity",message:h,severity:"warning"})))}return x(t.signal),f});y(e,"maxOutputBytes",i.byteLength);const{plan:g,...m}=c;return{...m,bytes:i,format:t.format,contentType:t.format==="pdf"?"application/pdf":"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet",stats:{...m.stats,durationMs:Date.now()-s,outputBytes:i.byteLength}}};return{describe:t=>Z(r.reports,t),validate:t=>z(r.reports,t),prepare:t=>F(t.signal,e.maxDurationMs,async s=>{const{signal:d,onEvent:u,...p}=t,c={...p,taskId:p.taskId??$.reportTaskId()},w=u?m=>$.notifyReportTaskEvent(u,m,s):void 0,i={...c,signal:s,onEvent:w};$.createReportTaskReporter(i).runSync("validate",()=>M(r,c));const g=r.executor?await r.executor.prepare(c,s,w):await n(i);return ee(g,e)}),export:t=>F(t.signal,e.maxDurationMs,async s=>{const{signal:d,onEvent:u,...p}=t,c={...p,taskId:p.taskId??$.reportTaskId()},w=u?m=>$.notifyReportTaskEvent(u,m,s):void 0,i={...c,signal:s,onEvent:w};if($.createReportTaskReporter(i).runSync("validate",()=>M(r,c)),c.format!=="pdf"&&c.format!=="xlsx")throw new P.ReportSourceError("config","不支持的报表导出格式");const g=r.executor?await r.executor.export(c,s,w):await a(i);return y(e,"maxRows",g.stats.rows),y(e,"maxPages",g.stats.pages),y(e,"maxCells",g.stats.cells),y(e,"maxOutputBytes",g.bytes.byteLength),{...g,stats:{...g.stats,outputBytes:g.bytes.byteLength}}})}}function re(r={}){const e=r.concurrency??1,n=r.maxQueued??20;if(!Number.isSafeInteger(e)||e<1||!Number.isSafeInteger(n)||n<0)throw new b("budget","队列并发应为正整数,排队上限应为非负整数");const a=[],t=new Set,s=new Set;let d=!1,u=0;const p=()=>{for(;!d&&t.size<e&&a.length;)a.shift().start()};return{get active(){return t.size},get pending(){return a.length},enqueue:(w,i={})=>{if(d)throw new b("closed","任务队列已关闭");if(x(i.signal),t.size>=e&&a.length>=n)throw new b("queue-full","报表任务队列已满");const g=i.id??`report-${++u}`;if(s.has(g))throw new b("queue-full","任务 ID 正在执行或排队");const m=new AbortController;let f="queued",l,o,h,R;const O=new Promise((v,E)=>{h=v,R=E}),j=()=>{i.signal?.removeEventListener("abort",q),s.delete(g)},k=v=>{if(f!=="queued"&&f!=="running")return;const E=f==="queued";f="cancelled",m.abort(v);try{x(m.signal)}catch(I){R(I)}if(E){const I=a.indexOf(S);I>=0&&a.splice(I,1),j(),p()}},q=()=>k(i.signal?.reason),L=(v,E)=>{f==="running"&&(!Number.isFinite(v)||v<0||E!==void 0&&(!Number.isFinite(E)||E<v)||(l={completed:v,...E===void 0?{}:{total:E}}))},J=v=>{f!=="running"||m.signal.aborted||(o={...v,taskId:g},v.completed!==void 0&&L(v.completed,v.total),$.notifyReportTaskEvent(i.onEvent,o,m.signal))},S={cancel:k,start:()=>{f==="queued"&&(f="running",t.add(S),Promise.resolve().then(()=>(x(m.signal),w({taskId:g,signal:m.signal,reportProgress:L,onEvent:J}))).then(v=>{f==="running"&&(f="completed",h(v))},v=>{f==="running"&&(f="failed",R(v))}).finally(()=>{t.delete(S),j(),p()}))}};return s.add(g),i.signal?.addEventListener("abort",q,{once:!0}),i.signal?.aborted?k(i.signal.reason):t.size<e?S.start():a.push(S),{id:g,get status(){return f},get progress(){return l},get event(){return o},result:O,cancel:k}},close:(w={})=>{d=!0;for(const i of[...a])i.cancel(new b("closed","任务队列已关闭"));if(w.cancelRunning)for(const i of t)i.cancel(new b("closed","任务队列已关闭"))}}}exports.ReportRuntimeError=b;exports.createReportRuntime=te;exports.createReportTaskQueue=re;
package/dist/server.d.cts CHANGED
@@ -446,12 +446,14 @@ export declare class ReportRuntimeError extends Error {
446
446
 
447
447
  /** 可用 worker_threads/进程/RPC 实现;接收可序列化请求,signal 由桥接层映射为取消消息。 */
448
448
  export declare interface ReportRuntimeExecutor {
449
- prepare(input: Omit<ReportRuntimeInput, "signal">, signal?: AbortSignal): Promise<PreparedReport>;
450
- export(input: Omit<ReportRuntimeExportInput, "signal">, signal?: AbortSignal): Promise<ReportRuntimeExportResult>;
449
+ prepare(input: Omit<ReportRuntimeInput, "signal" | "onEvent">, signal?: AbortSignal, onEvent?: ReportTaskObserver): Promise<PreparedReport>;
450
+ export(input: Omit<ReportRuntimeExportInput, "signal" | "onEvent">, signal?: AbortSignal, onEvent?: ReportTaskObserver): Promise<ReportRuntimeExportResult>;
451
451
  }
452
452
 
453
453
  export declare interface ReportRuntimeExportInput extends ReportRuntimeInput {
454
454
  format: "pdf" | "xlsx";
455
+ /** strict 在编码前拒绝已识别的输出降级;默认保留诊断并继续。 */
456
+ fidelity?: "warn" | "strict";
455
457
  /** PDF 中文需宿主显式提供有授权的字体;不隐式下载字体或资源。 */
456
458
  pdf?: {
457
459
  customFontBytes?: Uint8Array | ArrayBuffer;
@@ -476,7 +478,7 @@ export declare interface ReportRuntimeExportResult extends Omit<PreparedReport,
476
478
  contentType: string;
477
479
  }
478
480
 
479
- export declare interface ReportRuntimeInput {
481
+ export declare interface ReportRuntimeInput extends ReportTaskMonitoring {
480
482
  reportIds: string[];
481
483
  params?: Record<string, string>;
482
484
  signal?: AbortSignal;
@@ -520,6 +522,7 @@ declare interface ReportSaveResult {
520
522
  export declare interface ReportTask<T> {
521
523
  readonly id: string;
522
524
  readonly status: ReportTaskStatus;
525
+ readonly event: ReportTaskEvent | undefined;
523
526
  readonly progress: {
524
527
  completed: number;
525
528
  total?: number;
@@ -529,16 +532,38 @@ export declare interface ReportTask<T> {
529
532
  }
530
533
 
531
534
  export declare interface ReportTaskContext {
535
+ taskId: string;
532
536
  signal: AbortSignal;
537
+ onEvent: ReportTaskObserver;
533
538
  reportProgress(completed: number, total?: number): void;
534
539
  }
535
540
 
541
+ /** 阶段事件只包含可序列化值;不表示估算百分比,也不包含业务数据。 */
542
+ declare interface ReportTaskEvent {
543
+ taskId: string;
544
+ correlationId?: string;
545
+ stage: "query" | "validate" | "layout" | "encode";
546
+ status: "started" | "completed" | "failed";
547
+ reportId?: string;
548
+ completed?: number;
549
+ total?: number;
550
+ }
551
+
552
+ declare interface ReportTaskMonitoring {
553
+ taskId?: string;
554
+ correlationId?: string;
555
+ onEvent?: ReportTaskObserver;
556
+ }
557
+
558
+ declare type ReportTaskObserver = (event: ReportTaskEvent) => void;
559
+
536
560
  export declare interface ReportTaskQueue {
537
561
  readonly active: number;
538
562
  readonly pending: number;
539
563
  enqueue<T>(run: (context: ReportTaskContext) => T | Promise<T>, options?: {
540
564
  id?: string;
541
565
  signal?: AbortSignal;
566
+ onEvent?: ReportTaskObserver;
542
567
  }): ReportTask<T>;
543
568
  /** 关闭后拒绝新任务并取消排队任务;运行任务按参数发送取消信号。 */
544
569
  close(options?: {
package/dist/server.d.ts CHANGED
@@ -446,12 +446,14 @@ export declare class ReportRuntimeError extends Error {
446
446
 
447
447
  /** 可用 worker_threads/进程/RPC 实现;接收可序列化请求,signal 由桥接层映射为取消消息。 */
448
448
  export declare interface ReportRuntimeExecutor {
449
- prepare(input: Omit<ReportRuntimeInput, "signal">, signal?: AbortSignal): Promise<PreparedReport>;
450
- export(input: Omit<ReportRuntimeExportInput, "signal">, signal?: AbortSignal): Promise<ReportRuntimeExportResult>;
449
+ prepare(input: Omit<ReportRuntimeInput, "signal" | "onEvent">, signal?: AbortSignal, onEvent?: ReportTaskObserver): Promise<PreparedReport>;
450
+ export(input: Omit<ReportRuntimeExportInput, "signal" | "onEvent">, signal?: AbortSignal, onEvent?: ReportTaskObserver): Promise<ReportRuntimeExportResult>;
451
451
  }
452
452
 
453
453
  export declare interface ReportRuntimeExportInput extends ReportRuntimeInput {
454
454
  format: "pdf" | "xlsx";
455
+ /** strict 在编码前拒绝已识别的输出降级;默认保留诊断并继续。 */
456
+ fidelity?: "warn" | "strict";
455
457
  /** PDF 中文需宿主显式提供有授权的字体;不隐式下载字体或资源。 */
456
458
  pdf?: {
457
459
  customFontBytes?: Uint8Array | ArrayBuffer;
@@ -476,7 +478,7 @@ export declare interface ReportRuntimeExportResult extends Omit<PreparedReport,
476
478
  contentType: string;
477
479
  }
478
480
 
479
- export declare interface ReportRuntimeInput {
481
+ export declare interface ReportRuntimeInput extends ReportTaskMonitoring {
480
482
  reportIds: string[];
481
483
  params?: Record<string, string>;
482
484
  signal?: AbortSignal;
@@ -520,6 +522,7 @@ declare interface ReportSaveResult {
520
522
  export declare interface ReportTask<T> {
521
523
  readonly id: string;
522
524
  readonly status: ReportTaskStatus;
525
+ readonly event: ReportTaskEvent | undefined;
523
526
  readonly progress: {
524
527
  completed: number;
525
528
  total?: number;
@@ -529,16 +532,38 @@ export declare interface ReportTask<T> {
529
532
  }
530
533
 
531
534
  export declare interface ReportTaskContext {
535
+ taskId: string;
532
536
  signal: AbortSignal;
537
+ onEvent: ReportTaskObserver;
533
538
  reportProgress(completed: number, total?: number): void;
534
539
  }
535
540
 
541
+ /** 阶段事件只包含可序列化值;不表示估算百分比,也不包含业务数据。 */
542
+ declare interface ReportTaskEvent {
543
+ taskId: string;
544
+ correlationId?: string;
545
+ stage: "query" | "validate" | "layout" | "encode";
546
+ status: "started" | "completed" | "failed";
547
+ reportId?: string;
548
+ completed?: number;
549
+ total?: number;
550
+ }
551
+
552
+ declare interface ReportTaskMonitoring {
553
+ taskId?: string;
554
+ correlationId?: string;
555
+ onEvent?: ReportTaskObserver;
556
+ }
557
+
558
+ declare type ReportTaskObserver = (event: ReportTaskEvent) => void;
559
+
536
560
  export declare interface ReportTaskQueue {
537
561
  readonly active: number;
538
562
  readonly pending: number;
539
563
  enqueue<T>(run: (context: ReportTaskContext) => T | Promise<T>, options?: {
540
564
  id?: string;
541
565
  signal?: AbortSignal;
566
+ onEvent?: ReportTaskObserver;
542
567
  }): ReportTask<T>;
543
568
  /** 关闭后拒绝新任务并取消排队任务;运行任务按参数发送取消信号。 */
544
569
  close(options?: {
package/dist/server.js CHANGED
@@ -1,173 +1,177 @@
1
- import { d as q, R as $, c as k, P as z } from "./report-source-B9bENO0F.js";
2
- import { g as I } from "./report-params-B_VCihAh.js";
3
- import { b as L, r as J, R as V } from "./param-validation-BWNjLcN0.js";
4
- import { c as _ } from "./validate-S6CgIm5d.js";
5
- class p extends Error {
6
- constructor(e, a, s) {
7
- super(a), this.code = e, this.path = s, this.name = "ReportRuntimeError";
1
+ import { d as _, R as E, c as Q, P as W } from "./report-source-BXHNy_AD.js";
2
+ import { g as k } from "./report-params-B_VCihAh.js";
3
+ import { b as N, r as G, R as U } from "./param-validation-BWNjLcN0.js";
4
+ import { c as X } from "./validate-S6CgIm5d.js";
5
+ import { r as F, c as C, n as T } from "./task-events-Dpsvf_t2.js";
6
+ class b extends Error {
7
+ constructor(e, n, s) {
8
+ super(n), this.code = e, this.path = s, this.name = "ReportRuntimeError";
8
9
  }
9
10
  }
10
- function x(r) {
11
+ function y(r) {
11
12
  if (!r?.aborted) return;
12
- if (r.reason instanceof p) throw r.reason;
13
+ if (r.reason instanceof b) throw r.reason;
13
14
  const e = new Error("报表执行已取消");
14
15
  throw e.name = "AbortError", Object.defineProperty(e, "cause", { value: r.reason }), e;
15
16
  }
16
- function b(r, e, a) {
17
- if (!Number.isFinite(a) || a < 0) throw new p("budget", `${e} 的执行统计无效`, `$.budget.${e}`);
17
+ function x(r, e, n) {
18
+ if (!Number.isFinite(n) || n < 0) throw new b("budget", `${e} 的执行统计无效`, `$.budget.${e}`);
18
19
  const s = r[e];
19
- if (s !== void 0 && a > s) throw new p("budget", `${e} 超出预算 ${s}(实际 ${a})`, `$.budget.${e}`);
20
+ if (s !== void 0 && n > s) throw new b("budget", `${e} 超出预算 ${s}(实际 ${n})`, `$.budget.${e}`);
20
21
  }
21
- function Q(r) {
22
- for (const [e, a] of Object.entries(r)) {
23
- if (a !== void 0 && (!Number.isFinite(a) || a <= 0)) throw new p("budget", `${e} 应为正有限数字`, `$.budget.${e}`);
24
- if (e !== "maxDurationMs" && a !== void 0 && !Number.isSafeInteger(a)) throw new p("budget", `${e} 应为正安全整数`, `$.budget.${e}`);
25
- if (e === "maxDurationMs" && a !== void 0 && a > 2147483647) throw new p("budget", "maxDurationMs 不能超过 2147483647", `$.budget.${e}`);
22
+ function H(r) {
23
+ for (const [e, n] of Object.entries(r)) {
24
+ if (n !== void 0 && (!Number.isFinite(n) || n <= 0)) throw new b("budget", `${e} 应为正有限数字`, `$.budget.${e}`);
25
+ if (e !== "maxDurationMs" && n !== void 0 && !Number.isSafeInteger(n)) throw new b("budget", `${e} 应为正安全整数`, `$.budget.${e}`);
26
+ if (e === "maxDurationMs" && n !== void 0 && n > 2147483647) throw new b("budget", "maxDurationMs 不能超过 2147483647", `$.budget.${e}`);
26
27
  }
27
28
  }
28
- async function B(r, e, a) {
29
+ async function A(r, e, n) {
29
30
  const s = new AbortController(), t = () => s.abort(r?.reason);
30
31
  r?.addEventListener("abort", t, { once: !0 }), r?.aborted && t();
31
- const n = Date.now(), l = e === void 0 ? void 0 : setTimeout(() => s.abort(new p("timeout", `报表执行超过 ${e}ms`)), e);
32
- let o;
32
+ const a = Date.now(), u = e === void 0 ? void 0 : setTimeout(() => s.abort(new b("timeout", `报表执行超过 ${e}ms`)), e);
33
+ let d;
33
34
  try {
34
- x(s.signal);
35
- const i = new Promise((w, f) => {
36
- o = () => {
35
+ y(s.signal);
36
+ const m = new Promise((w, i) => {
37
+ d = () => {
37
38
  try {
38
- x(s.signal);
39
- } catch (v) {
40
- f(v);
39
+ y(s.signal);
40
+ } catch (g) {
41
+ i(g);
41
42
  }
42
- }, s.signal.addEventListener("abort", o, { once: !0 });
43
- }), m = await Promise.race([a(s.signal), i]);
44
- if (x(s.signal), e !== void 0 && Date.now() - n > e) throw new p("timeout", `报表执行超过 ${e}ms`);
45
- return m;
43
+ }, s.signal.addEventListener("abort", d, { once: !0 });
44
+ }), c = await Promise.race([n(s.signal), m]);
45
+ if (y(s.signal), e !== void 0 && Date.now() - a > e) throw new b("timeout", `报表执行超过 ${e}ms`);
46
+ return c;
46
47
  } finally {
47
- l !== void 0 && clearTimeout(l), o && s.signal.removeEventListener("abort", o), r?.removeEventListener("abort", t);
48
+ u !== void 0 && clearTimeout(u), d && s.signal.removeEventListener("abort", d), r?.removeEventListener("abort", t);
48
49
  }
49
50
  }
50
- function F(r, e) {
51
- if (e.length === 0) throw new $("config", "缺少报表 ID");
52
- return e.map((a) => {
53
- if (!Object.prototype.hasOwnProperty.call(r, a)) throw new $("config", `未注册报表 ${a}`);
54
- return r[a];
51
+ function z(r, e) {
52
+ if (e.length === 0) throw new E("config", "缺少报表 ID");
53
+ return e.map((n) => {
54
+ if (!Object.prototype.hasOwnProperty.call(r, n)) throw new E("config", `未注册报表 ${n}`);
55
+ return r[n];
55
56
  });
56
57
  }
57
- function S(r) {
58
- return r.grid?.cells.reduce((e, a) => e + a.reduce((s, t) => s + (t ? 1 + (t.children?.reduce((n, l) => n + S(l), 0) ?? 0) : 0), 0), 0) ?? 0;
58
+ function D(r) {
59
+ return r.grid?.cells.reduce((e, n) => e + n.reduce((s, t) => s + (t ? 1 + (t.children?.reduce((a, u) => a + D(u), 0) ?? 0) : 0), 0), 0) ?? 0;
59
60
  }
60
- function W(r, e) {
61
- return r.pages.reduce((a, s) => a + s.components.reduce((t, n) => {
62
- if (n.kind !== "list") return t + S(n);
63
- const l = e[n.dataset]?.length ?? 0;
64
- return t + n.columns.length * (l + (n.headerGrid?.cells.length ?? 1));
61
+ function K(r, e) {
62
+ return r.pages.reduce((n, s) => n + s.components.reduce((t, a) => {
63
+ if (a.kind !== "list") return t + D(a);
64
+ const u = e[a.dataset]?.length ?? 0;
65
+ return t + a.columns.length * (u + (a.headerGrid?.cells.length ?? 1));
65
66
  }, 0), 0);
66
67
  }
67
- function G(r, e = Object.keys(r)) {
68
- return F(r, e).map((a, s) => {
69
- const t = e[s], n = I(r, [t]);
68
+ function Y(r, e = Object.keys(r)) {
69
+ return z(r, e).map((n, s) => {
70
+ const t = e[s], a = k(r, [t]);
70
71
  return {
71
72
  id: t,
72
- params: JSON.parse(JSON.stringify(n)),
73
- paramsSchema: J(n),
74
- datasetsSchema: Object.fromEntries(Object.entries(a.dataSchema ?? {}).map(([l, o]) => [l, q(o)])),
73
+ params: JSON.parse(JSON.stringify(a)),
74
+ paramsSchema: G(a),
75
+ datasetsSchema: Object.fromEntries(Object.entries(n.dataSchema ?? {}).map(([u, d]) => [u, _(d)])),
75
76
  capabilities: {
76
- save: !!a.provider?.save,
77
- export: !!a.provider?.export,
78
- templates: !!a.provider?.templates
77
+ save: !!n.provider?.save,
78
+ export: !!n.provider?.export,
79
+ templates: !!n.provider?.templates
79
80
  }
80
81
  };
81
82
  });
82
83
  }
83
- function A(r, e) {
84
- F(r, e.reportIds);
85
- const a = L(I(r, e.reportIds), e.params), s = e.reportIds.flatMap((n) => L(I(r, [n]), e.params).issues), t = new Map(s.map((n) => [JSON.stringify(n), n]));
86
- return { ...a, ok: t.size === 0, issues: [...t.values()] };
84
+ function J(r, e) {
85
+ z(r, e.reportIds);
86
+ const n = N(k(r, e.reportIds), e.params), s = e.reportIds.flatMap((a) => N(k(r, [a]), e.params).issues), t = new Map(s.map((a) => [JSON.stringify(a), a]));
87
+ return { ...n, ok: t.size === 0, issues: [...t.values()] };
87
88
  }
88
- function U(r, e) {
89
- const a = _(r.plan);
90
- if (!a.ok) throw new $("validate", `执行器返回无效计划:${a.errors[0]?.path}`);
91
- const s = r.plan.pages.length, t = r.plan.pages.reduce((n, l) => n + l.components.reduce((o, i) => o + S(i), 0), 0);
92
- return b(e, "maxRows", r.stats.rows), b(e, "maxPages", s), b(e, "maxCells", t), { ...r, stats: { ...r.stats, pages: s, cells: t } };
89
+ function Z(r, e) {
90
+ const n = X(r.plan);
91
+ if (!n.ok) throw new E("validate", `执行器返回无效计划:${n.errors[0]?.path}`);
92
+ const s = r.plan.pages.length, t = r.plan.pages.reduce((a, u) => a + u.components.reduce((d, m) => d + D(m), 0), 0);
93
+ return x(e, "maxRows", r.stats.rows), x(e, "maxPages", s), x(e, "maxCells", t), { ...r, stats: { ...r.stats, pages: s, cells: t } };
93
94
  }
94
- function N(r, e) {
95
- const a = A(r.reports, e);
96
- if (!a.ok) throw new V(a.issues);
95
+ function M(r, e) {
96
+ const n = J(r.reports, e);
97
+ if (!n.ok) throw new U(n.issues);
97
98
  }
98
- function T(r = []) {
99
- return r.map(({ code: e, message: a, severity: s, pageIndex: t, componentIndex: n }) => ({ code: e, message: a, severity: s, path: `$.pages.${t}.components.${n}` }));
99
+ function q(r = []) {
100
+ return r.map(({ code: e, message: n, severity: s, pageIndex: t, componentIndex: a }) => ({ code: e, message: n, severity: s, path: `$.pages.${t}.components.${a}` }));
100
101
  }
101
- function Z(r) {
102
+ function ae(r) {
102
103
  const e = { maxRows: 1e5, maxPages: 1e4, maxCells: 2e6, maxOutputBytes: 1e8, maxDurationMs: 12e4, ...r.budget };
103
- Q(e);
104
- const a = async (t, n) => {
105
- const l = Date.now();
106
- let o = 0, i = 0;
107
- const m = [], w = {}, f = Object.fromEntries(Object.entries(r.reports).map(([d, g]) => [d, {
108
- ...g,
109
- pagination: { ...r.pagination, ...g.pagination, ...n ? { measurer: n } : {} },
104
+ H(e);
105
+ const n = async (t, a) => {
106
+ const u = Date.now();
107
+ let d = 0, m = 0;
108
+ const c = [], w = {}, i = Object.fromEntries(Object.entries(r.reports).map(([l, o]) => [l, {
109
+ ...o,
110
+ pagination: { ...r.pagination, ...o.pagination, ...a ? { measurer: a } : {} },
110
111
  dataValidation: {
111
- ...g.dataValidation,
112
- maxRows: Math.min(e.maxRows ?? 1e5, g.dataValidation?.maxRows ?? 1 / 0),
113
- maxCells: Math.min(e.maxCells ?? 2e6, g.dataValidation?.maxCells ?? 1 / 0)
112
+ ...o.dataValidation,
113
+ maxRows: Math.min(e.maxRows ?? 1e5, o.dataValidation?.maxRows ?? 1 / 0),
114
+ maxCells: Math.min(e.maxCells ?? 2e6, o.dataValidation?.maxCells ?? 1 / 0)
114
115
  }
115
- }])), u = await k(f, { maxPages: e.maxPages, onDatasets: (d, g, P) => {
116
- o += Object.values(g).reduce((R, O) => R + O.length, 0), b(e, "maxRows", o), i += W(P, g), b(e, "maxCells", i);
117
- } })({ ...t, params: t.params ?? {}, onWarning: (d) => m.push({ code: "layout", message: d, severity: "warning" }), onQueryResult: (d, g) => {
118
- Object.defineProperty(w, d, { value: { revision: g.revision, sourceToken: g.sourceToken }, enumerable: !0, writable: !0 }), m.push(...g.diagnostics ?? []);
119
- } }).catch((d) => {
120
- throw d instanceof $ && d.cause instanceof z ? new p("budget", d.cause.message, "$.budget.maxPages") : d;
116
+ }])), p = await Q(i, { maxPages: e.maxPages, onDatasets: (l, o, v) => {
117
+ d += Object.values(o).reduce((P, S) => P + S.length, 0), x(e, "maxRows", d), m += K(v, o), x(e, "maxCells", m);
118
+ } })({ ...t, params: t.params ?? {}, onWarning: (l) => c.push({ code: "layout", message: l, severity: "warning" }), onQueryResult: (l, o) => {
119
+ Object.defineProperty(w, l, { value: { revision: o.revision, sourceToken: o.sourceToken }, enumerable: !0, writable: !0 }), c.push(...o.diagnostics ?? []);
120
+ } }).catch((l) => {
121
+ throw l instanceof E && l.cause instanceof W ? new b("budget", l.cause.message, "$.budget.maxPages") : l;
121
122
  });
122
- x(t.signal);
123
- const c = u.pages.reduce((d, g) => d + g.components.reduce((P, R) => P + S(R), 0), 0);
124
- return b(e, "maxPages", u.pages.length), b(e, "maxCells", c), { plan: u, diagnostics: m, revisions: w, stats: { rows: o, pages: u.pages.length, cells: c, durationMs: Date.now() - l } };
123
+ y(t.signal);
124
+ const f = p.pages.reduce((l, o) => l + o.components.reduce((v, P) => v + D(P), 0), 0);
125
+ return x(e, "maxPages", p.pages.length), x(e, "maxCells", f), { plan: p, diagnostics: c, revisions: w, stats: { rows: d, pages: p.pages.length, cells: f, durationMs: Date.now() - u } };
125
126
  }, s = async (t) => {
126
- const n = Date.now();
127
- if (t.format !== "pdf" && t.format !== "xlsx") throw new $("config", "不支持的报表导出格式");
128
- const l = t.format === "pdf" ? await import("@agile-team/mach-report/pdf") : void 0;
129
- x(t.signal);
130
- const o = t.pdf?.customFontFaces ?? (t.pdf?.customFontBytes ? { regular: t.pdf.customFontBytes } : void 0), i = l && o ? l.createFontBytesMeasurer(o) : void 0, m = await a(t, i);
131
- x(t.signal);
132
- let w;
133
- if (t.format === "pdf") {
134
- x(t.signal);
135
- const u = await l.renderPlanToPdf(m.plan, { ...t.pdf, ...i ? { measurer: i } : {} });
136
- w = u.bytes, m.diagnostics.push(...T(u.diagnostics)), m.diagnostics.push(...u.fidelityWarnings.map((c) => ({ code: "pdf-fidelity", message: c, severity: "warning" })), ...u.pageErrors.map((c) => ({ code: "pdf-page", message: c, severity: "error" }))), u.unsupportedTextCount && m.diagnostics.push({ code: "pdf-font", message: `${u.unsupportedTextCount} 段文本包含当前字体不支持的字符`, severity: "warning" });
137
- } else {
138
- const { renderPlanToXlsx: u } = await import("@agile-team/mach-report/xlsx");
139
- x(t.signal);
140
- const c = await u(m.plan, t.xlsx);
141
- w = new Uint8Array(c.buffer), m.diagnostics.push(...T(c.diagnostics)), m.diagnostics.push(...c.warnings.map((d) => ({ code: "xlsx-fidelity", message: d, severity: "warning" })));
142
- }
143
- x(t.signal), b(e, "maxOutputBytes", w.byteLength);
144
- const { plan: f, ...v } = m;
145
- return { ...v, bytes: w, format: t.format, contentType: t.format === "pdf" ? "application/pdf" : "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet", stats: { ...v.stats, durationMs: Date.now() - n, outputBytes: w.byteLength } };
127
+ const a = Date.now();
128
+ if (t.format !== "pdf" && t.format !== "xlsx") throw new E("config", "不支持的报表导出格式");
129
+ const u = t.format === "pdf" ? await import("@agile-team/mach-report/pdf") : void 0;
130
+ y(t.signal);
131
+ const d = t.pdf?.customFontFaces ?? (t.pdf?.customFontBytes ? { regular: t.pdf.customFontBytes } : void 0), m = u && d ? u.createFontBytesMeasurer(d) : void 0, c = await n(t, m);
132
+ y(t.signal);
133
+ const w = C(t), i = await w.run("encode", async () => {
134
+ let f;
135
+ if (t.format === "pdf") {
136
+ y(t.signal);
137
+ const l = await u.renderPlanToPdf(c.plan, { ...t.pdf, ...m ? { measurer: m } : {}, fidelity: t.fidelity, signal: t.signal, onProgress: (o, v) => w.progress("encode", o, v) });
138
+ f = l.bytes, c.diagnostics.push(...q(l.diagnostics)), c.diagnostics.push(...l.fidelityWarnings.map((o) => ({ code: "pdf-fidelity", message: o, severity: "warning" })), ...l.pageErrors.map((o) => ({ code: "pdf-page", message: o, severity: "error" }))), l.unsupportedTextCount && c.diagnostics.push({ code: "pdf-font", message: `${l.unsupportedTextCount} 段文本包含当前字体不支持的字符`, severity: "warning" });
139
+ } else {
140
+ const { renderPlanToXlsx: l } = await import("@agile-team/mach-report/xlsx");
141
+ y(t.signal);
142
+ const o = await l(c.plan, { ...t.xlsx, fidelity: t.fidelity, signal: t.signal, onProgress: (v, P) => w.progress("encode", v, P) });
143
+ f = new Uint8Array(o.buffer), c.diagnostics.push(...q(o.diagnostics)), c.diagnostics.push(...o.warnings.map((v) => ({ code: "xlsx-fidelity", message: v, severity: "warning" })));
144
+ }
145
+ return y(t.signal), f;
146
+ });
147
+ x(e, "maxOutputBytes", i.byteLength);
148
+ const { plan: g, ...p } = c;
149
+ return { ...p, bytes: i, format: t.format, contentType: t.format === "pdf" ? "application/pdf" : "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet", stats: { ...p.stats, durationMs: Date.now() - a, outputBytes: i.byteLength } };
146
150
  };
147
151
  return {
148
- describe: (t) => G(r.reports, t),
149
- validate: (t) => A(r.reports, t),
150
- prepare: (t) => B(t.signal, e.maxDurationMs, async (n) => {
151
- const { signal: l, ...o } = t;
152
- N(r, o);
153
- const i = r.executor ? await r.executor.prepare(o, n) : await a({ ...o, signal: n });
154
- return U(i, e);
152
+ describe: (t) => Y(r.reports, t),
153
+ validate: (t) => J(r.reports, t),
154
+ prepare: (t) => A(t.signal, e.maxDurationMs, async (a) => {
155
+ const { signal: u, onEvent: d, ...m } = t, c = { ...m, taskId: m.taskId ?? F() }, w = d ? (p) => T(d, p, a) : void 0, i = { ...c, signal: a, onEvent: w };
156
+ C(i).runSync("validate", () => M(r, c));
157
+ const g = r.executor ? await r.executor.prepare(c, a, w) : await n(i);
158
+ return Z(g, e);
155
159
  }),
156
- export: (t) => B(t.signal, e.maxDurationMs, async (n) => {
157
- const { signal: l, ...o } = t;
158
- if (N(r, o), o.format !== "pdf" && o.format !== "xlsx") throw new $("config", "不支持的报表导出格式");
159
- const i = r.executor ? await r.executor.export(o, n) : await s({ ...o, signal: n });
160
- return b(e, "maxRows", i.stats.rows), b(e, "maxPages", i.stats.pages), b(e, "maxCells", i.stats.cells), b(e, "maxOutputBytes", i.bytes.byteLength), { ...i, stats: { ...i.stats, outputBytes: i.bytes.byteLength } };
160
+ export: (t) => A(t.signal, e.maxDurationMs, async (a) => {
161
+ const { signal: u, onEvent: d, ...m } = t, c = { ...m, taskId: m.taskId ?? F() }, w = d ? (p) => T(d, p, a) : void 0, i = { ...c, signal: a, onEvent: w };
162
+ if (C(i).runSync("validate", () => M(r, c)), c.format !== "pdf" && c.format !== "xlsx") throw new E("config", "不支持的报表导出格式");
163
+ const g = r.executor ? await r.executor.export(c, a, w) : await s(i);
164
+ return x(e, "maxRows", g.stats.rows), x(e, "maxPages", g.stats.pages), x(e, "maxCells", g.stats.cells), x(e, "maxOutputBytes", g.bytes.byteLength), { ...g, stats: { ...g.stats, outputBytes: g.bytes.byteLength } };
161
165
  })
162
166
  };
163
167
  }
164
- function ee(r = {}) {
165
- const e = r.concurrency ?? 1, a = r.maxQueued ?? 20;
166
- if (!Number.isSafeInteger(e) || e < 1 || !Number.isSafeInteger(a) || a < 0) throw new p("budget", "队列并发应为正整数,排队上限应为非负整数");
167
- const s = [], t = /* @__PURE__ */ new Set(), n = /* @__PURE__ */ new Set();
168
- let l = !1, o = 0;
169
- const i = () => {
170
- for (; !l && t.size < e && s.length; ) s.shift().start();
168
+ function oe(r = {}) {
169
+ const e = r.concurrency ?? 1, n = r.maxQueued ?? 20;
170
+ if (!Number.isSafeInteger(e) || e < 1 || !Number.isSafeInteger(n) || n < 0) throw new b("budget", "队列并发应为正整数,排队上限应为非负整数");
171
+ const s = [], t = /* @__PURE__ */ new Set(), a = /* @__PURE__ */ new Set();
172
+ let u = !1, d = 0;
173
+ const m = () => {
174
+ for (; !u && t.size < e && s.length; ) s.shift().start();
171
175
  };
172
176
  return {
173
177
  get active() {
@@ -176,62 +180,66 @@ function ee(r = {}) {
176
180
  get pending() {
177
181
  return s.length;
178
182
  },
179
- enqueue: (w, f = {}) => {
180
- if (l) throw new p("closed", "任务队列已关闭");
181
- if (x(f.signal), t.size >= e && s.length >= a) throw new p("queue-full", "报表任务队列已满");
182
- const v = f.id ?? `report-${++o}`;
183
- if (n.has(v)) throw new p("queue-full", "任务 ID 正在执行或排队");
184
- const u = new AbortController();
185
- let c = "queued", d, g, P;
186
- const R = new Promise((h, y) => {
187
- g = h, P = y;
188
- }), O = () => {
189
- f.signal?.removeEventListener("abort", j), n.delete(v);
190
- }, D = (h) => {
191
- if (c !== "queued" && c !== "running") return;
192
- const y = c === "queued";
193
- c = "cancelled", u.abort(h);
183
+ enqueue: (w, i = {}) => {
184
+ if (u) throw new b("closed", "任务队列已关闭");
185
+ if (y(i.signal), t.size >= e && s.length >= n) throw new b("queue-full", "报表任务队列已满");
186
+ const g = i.id ?? `report-${++d}`;
187
+ if (a.has(g)) throw new b("queue-full", "任务 ID 正在执行或排队");
188
+ const p = new AbortController();
189
+ let f = "queued", l, o, v, P;
190
+ const S = new Promise((h, R) => {
191
+ v = h, P = R;
192
+ }), j = () => {
193
+ i.signal?.removeEventListener("abort", L), a.delete(g);
194
+ }, I = (h) => {
195
+ if (f !== "queued" && f !== "running") return;
196
+ const R = f === "queued";
197
+ f = "cancelled", p.abort(h);
194
198
  try {
195
- x(u.signal);
196
- } catch (C) {
197
- P(C);
199
+ y(p.signal);
200
+ } catch (O) {
201
+ P(O);
198
202
  }
199
- if (y) {
200
- const C = s.indexOf(E);
201
- C >= 0 && s.splice(C, 1), O(), i();
203
+ if (R) {
204
+ const O = s.indexOf($);
205
+ O >= 0 && s.splice(O, 1), j(), m();
202
206
  }
203
- }, j = () => D(f.signal?.reason), M = (h, y) => {
204
- c === "running" && (!Number.isFinite(h) || h < 0 || y !== void 0 && (!Number.isFinite(y) || y < h) || (d = { completed: h, ...y === void 0 ? {} : { total: y } }));
205
- }, E = {
206
- cancel: D,
207
+ }, L = () => I(i.signal?.reason), B = (h, R) => {
208
+ f === "running" && (!Number.isFinite(h) || h < 0 || R !== void 0 && (!Number.isFinite(R) || R < h) || (l = { completed: h, ...R === void 0 ? {} : { total: R } }));
209
+ }, V = (h) => {
210
+ f !== "running" || p.signal.aborted || (o = { ...h, taskId: g }, h.completed !== void 0 && B(h.completed, h.total), T(i.onEvent, o, p.signal));
211
+ }, $ = {
212
+ cancel: I,
207
213
  start: () => {
208
- c === "queued" && (c = "running", t.add(E), Promise.resolve().then(() => (x(u.signal), w({ signal: u.signal, reportProgress: M }))).then(
214
+ f === "queued" && (f = "running", t.add($), Promise.resolve().then(() => (y(p.signal), w({ taskId: g, signal: p.signal, reportProgress: B, onEvent: V }))).then(
209
215
  (h) => {
210
- c === "running" && (c = "completed", g(h));
216
+ f === "running" && (f = "completed", v(h));
211
217
  },
212
218
  (h) => {
213
- c === "running" && (c = "failed", P(h));
219
+ f === "running" && (f = "failed", P(h));
214
220
  }
215
221
  ).finally(() => {
216
- t.delete(E), O(), i();
222
+ t.delete($), j(), m();
217
223
  }));
218
224
  }
219
225
  };
220
- return n.add(v), f.signal?.addEventListener("abort", j, { once: !0 }), f.signal?.aborted ? D(f.signal.reason) : t.size < e ? E.start() : s.push(E), { id: v, get status() {
221
- return c;
226
+ return a.add(g), i.signal?.addEventListener("abort", L, { once: !0 }), i.signal?.aborted ? I(i.signal.reason) : t.size < e ? $.start() : s.push($), { id: g, get status() {
227
+ return f;
222
228
  }, get progress() {
223
- return d;
224
- }, result: R, cancel: D };
229
+ return l;
230
+ }, get event() {
231
+ return o;
232
+ }, result: S, cancel: I };
225
233
  },
226
234
  close: (w = {}) => {
227
- l = !0;
228
- for (const f of [...s]) f.cancel(new p("closed", "任务队列已关闭"));
229
- if (w.cancelRunning) for (const f of t) f.cancel(new p("closed", "任务队列已关闭"));
235
+ u = !0;
236
+ for (const i of [...s]) i.cancel(new b("closed", "任务队列已关闭"));
237
+ if (w.cancelRunning) for (const i of t) i.cancel(new b("closed", "任务队列已关闭"));
230
238
  }
231
239
  };
232
240
  }
233
241
  export {
234
- p as ReportRuntimeError,
235
- Z as createReportRuntime,
236
- ee as createReportTaskQueue
242
+ b as ReportRuntimeError,
243
+ ae as createReportRuntime,
244
+ oe as createReportTaskQueue
237
245
  };