11import { extname } from "node:path" ;
22import type { DaemonClient , JsonValue } from "@univer-cli/daemon" ;
33import {
4- UnitExchangeFormat ,
5- type ImportableUnitType ,
6- type UnitExchange ,
7- type UnitExchangeData ,
8- } from "@univer-cli/unit-exchange" ;
4+ ExchangeFormat ,
5+ FormulaCalculationMode ,
6+ exportToFile ,
7+ importFile ,
8+ type ExportOptions ,
9+ type ImportOptions ,
10+ } from "@univerjs-pro/exchange-node" ;
911import { UniverInstanceType } from "@univerjs/core" ;
1012import { workspaceError } from "../../errors.js" ;
1113import type { WorkspaceRuntimeTarget } from "../../runtime/target.js" ;
1214import type { WorkspaceUnitType } from "../space/model.js" ;
1315import type { WorkspaceUnit } from "../worktree/model.js" ;
1416
17+ type WorkspaceExchangeUnitType =
18+ | UniverInstanceType . UNIVER_SHEET
19+ | UniverInstanceType . UNIVER_BASE
20+ | UniverInstanceType . UNIVER_DOC
21+ | UniverInstanceType . UNIVER_SLIDE ;
22+ type ImportOfficeFile = (
23+ path : string ,
24+ options : ImportOptions ,
25+ ) => Promise < Readonly < Record < string , unknown > > > ;
26+ type ExportOfficeFile = (
27+ data : Readonly < Record < string , JsonValue > > ,
28+ path : string ,
29+ options : ExportOptions ,
30+ ) => Promise < void > ;
31+
32+ const importOfficeFile = importFile as unknown as ImportOfficeFile ;
33+ const exportOfficeFile = exportToFile as unknown as ExportOfficeFile ;
34+
1535export interface WorkspaceUnitExchangeDependencies {
1636 readonly daemon : Pick < DaemonClient , "request" > ;
17- readonly exchange : UnitExchange ;
37+ readonly exportToFile ?: ExportOfficeFile ;
38+ readonly importFile ?: ImportOfficeFile ;
1839 readonly createUnit : ( input : {
1940 readonly idempotencyKey ?: string ;
2041 readonly initialData : Readonly < Record < string , unknown > > ;
@@ -70,18 +91,18 @@ export class WorkspaceUnitExchangeFeature {
7091 public async importFile ( input : WorkspaceImportFileInput ) : Promise < WorkspaceImportFileResult > {
7192 const type = inferImportType ( input . sourcePath , input . type ) ;
7293 const unitType = toInstanceType ( type ) ;
73- const imported = await this . dependencies . exchange . importFile ( {
74- sourcePath : input . sourcePath ,
75- unitType,
76- } ) ;
94+ const imported = await ( this . dependencies . importFile ?? importOfficeFile ) (
95+ input . sourcePath ,
96+ importOptions ( input . sourcePath , unitType ) ,
97+ ) ;
7798 const explicitName = nonEmpty ( input . name ) ;
7899 const name =
79100 explicitName ??
80- nonEmpty ( "name" in imported . data ? imported . data . name : undefined ) ??
81- nonEmpty ( "title" in imported . data ? imported . data . title : undefined ) ??
101+ nonEmpty ( imported [ "name" ] ) ??
102+ nonEmpty ( imported [ "title" ] ) ??
82103 `Imported ${ type } ` ;
83104 const initialData = {
84- ...imported . data ,
105+ ...imported ,
85106 ...( explicitName === undefined ? { } : { name : explicitName } ) ,
86107 } as Readonly < Record < string , unknown > > ;
87108 const created = await this . dependencies . createUnit ( {
@@ -129,7 +150,13 @@ export class WorkspaceUnitExchangeFeature {
129150 `Workspace runtime exported invalid UnitData for ${ target . unitId } .` ,
130151 ) ;
131152 }
132- await exportUnit ( this . dependencies . exchange , target . unitType , result , format , input . outputPath ) ;
153+ await exportUnit (
154+ this . dependencies . exportToFile ?? exportOfficeFile ,
155+ target . unitType ,
156+ result ,
157+ format ,
158+ input . outputPath ,
159+ ) ;
133160 return {
134161 outputPath : input . outputPath ,
135162 type : target . unitType ,
@@ -159,14 +186,14 @@ function inferImportType(
159186 ) ;
160187}
161188
162- function inferExportFormat ( outputPath : string ) : UnitExchangeFormat {
189+ function inferExportFormat ( outputPath : string ) : ExchangeFormat {
163190 switch ( extname ( outputPath ) . toLowerCase ( ) ) {
164191 case ".xlsx" :
165- return UnitExchangeFormat . XLSX ;
192+ return ExchangeFormat . XLSX ;
166193 case ".docx" :
167- return UnitExchangeFormat . DOCX ;
194+ return ExchangeFormat . DOCX ;
168195 case ".pptx" :
169- return UnitExchangeFormat . PPTX ;
196+ return ExchangeFormat . PPTX ;
170197 default :
171198 throw workspaceError (
172199 "workspace-exchange-export-format-unsupported" ,
@@ -177,12 +204,12 @@ function inferExportFormat(outputPath: string): UnitExchangeFormat {
177204
178205function requireCompatibleExport (
179206 type : Exclude < WorkspaceUnitType , "board" > ,
180- format : UnitExchangeFormat ,
207+ format : ExchangeFormat ,
181208) : void {
182209 const compatible =
183- ( ( type === "sheet" || type === "base" ) && format === UnitExchangeFormat . XLSX ) ||
184- ( type === "doc" && format === UnitExchangeFormat . DOCX ) ||
185- ( type === "slide" && format === UnitExchangeFormat . PPTX ) ;
210+ ( ( type === "sheet" || type === "base" ) && format === ExchangeFormat . XLSX ) ||
211+ ( type === "doc" && format === ExchangeFormat . DOCX ) ||
212+ ( type === "slide" && format === ExchangeFormat . PPTX ) ;
186213 if ( ! compatible ) {
187214 throw workspaceError (
188215 "workspace-exchange-export-format-mismatch" ,
@@ -191,7 +218,7 @@ function requireCompatibleExport(
191218 }
192219}
193220
194- function toInstanceType ( type : Exclude < WorkspaceUnitType , "board" > ) : ImportableUnitType {
221+ function toInstanceType ( type : Exclude < WorkspaceUnitType , "board" > ) : WorkspaceExchangeUnitType {
195222 switch ( type ) {
196223 case "sheet" :
197224 return UniverInstanceType . UNIVER_SHEET ;
@@ -205,14 +232,34 @@ function toInstanceType(type: Exclude<WorkspaceUnitType, "board">): ImportableUn
205232}
206233
207234async function exportUnit (
208- exchange : UnitExchange ,
235+ exchange : ExportOfficeFile ,
209236 type : Exclude < WorkspaceUnitType , "board" > ,
210237 data : Record < string , JsonValue > ,
211- format : UnitExchangeFormat ,
238+ format : ExchangeFormat ,
212239 outputPath : string ,
213240) : Promise < void > {
214- const unit = { data, type : toInstanceType ( type ) } as unknown as UnitExchangeData ;
215- await exchange . exportFile ( { unit, format, outputPath } ) ;
241+ const unitType = toInstanceType ( type ) ;
242+ await exchange ( data , outputPath , {
243+ format,
244+ type : unitType ,
245+ ...( unitType === UniverInstanceType . UNIVER_SHEET
246+ ? { formulaCalculation : FormulaCalculationMode . FORCED }
247+ : { } ) ,
248+ } as ExportOptions ) ;
249+ }
250+
251+ function importOptions ( sourcePath : string , type : WorkspaceExchangeUnitType ) : ImportOptions {
252+ const extension = extname ( sourcePath ) . toLowerCase ( ) ;
253+ const format = [ ".pptm" , ".ppsx" , ".ppsm" , ".potx" ] . includes ( extension )
254+ ? ExchangeFormat . PPTX
255+ : undefined ;
256+ return {
257+ type,
258+ ...( format === undefined ? { } : { format } ) ,
259+ ...( type === UniverInstanceType . UNIVER_SHEET && extension === ".xlsx"
260+ ? { formulaCalculation : FormulaCalculationMode . FORCED }
261+ : { } ) ,
262+ } as ImportOptions ;
216263}
217264
218265function requireCreatedUnit (
0 commit comments