Skip to content

Commit 0f70f64

Browse files
committed
BridgeJS: Properly treat exposeToGlobal on module level
1 parent afe86fc commit 0f70f64

File tree

1 file changed

+71
-53
lines changed

1 file changed

+71
-53
lines changed

Plugins/BridgeJS/Sources/BridgeJSLink/BridgeJSLink.swift

Lines changed: 71 additions & 53 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,6 @@ struct BridgeJSLink {
1212
var exportedSkeletons: [ExportedSkeleton] = []
1313
var importedSkeletons: [ImportedModuleSkeleton] = []
1414
let sharedMemory: Bool
15-
var exposeToGlobal: Bool
1615
private let namespaceBuilder = NamespaceBuilder()
1716

1817
init(
@@ -23,15 +22,11 @@ struct BridgeJSLink {
2322
self.exportedSkeletons = exportedSkeletons
2423
self.importedSkeletons = importedSkeletons
2524
self.sharedMemory = sharedMemory
26-
self.exposeToGlobal = exportedSkeletons.contains { $0.exposeToGlobal }
2725
}
2826

2927
mutating func addExportedSkeletonFile(data: Data) throws {
3028
let skeleton = try JSONDecoder().decode(ExportedSkeleton.self, from: data)
3129
exportedSkeletons.append(skeleton)
32-
if skeleton.exposeToGlobal {
33-
exposeToGlobal = true
34-
}
3530
}
3631

3732
mutating func addImportedSkeletonFile(data: Data) throws {
@@ -929,7 +924,6 @@ struct BridgeJSLink {
929924
// Type definitions section (namespace declarations, class definitions, imported types)
930925
let namespaceDeclarationsLines = namespaceBuilder.namespaceDeclarations(
931926
exportedSkeletons: exportedSkeletons,
932-
exposeToGlobal: exposeToGlobal,
933927
renderTSSignatureCallback: { parameters, returnType, effects in
934928
self.renderTSSignature(parameters: parameters, returnType: returnType, effects: effects)
935929
}
@@ -1012,8 +1006,7 @@ struct BridgeJSLink {
10121006
printer.write(lines: data.topLevelEnumLines)
10131007

10141008
let topLevelNamespaceCode = namespaceBuilder.buildTopLevelNamespaceInitialization(
1015-
exportedSkeletons: exportedSkeletons,
1016-
exposeToGlobal: exposeToGlobal
1009+
exportedSkeletons: exportedSkeletons
10171010
)
10181011
printer.write(lines: topLevelNamespaceCode)
10191012

@@ -1076,16 +1069,14 @@ struct BridgeJSLink {
10761069
printer.write(lines: data.classLines)
10771070

10781071
let namespaceInitCode = namespaceBuilder.buildNamespaceInitialization(
1079-
exportedSkeletons: exportedSkeletons,
1080-
exposeToGlobal: exposeToGlobal
1072+
exportedSkeletons: exportedSkeletons
10811073
)
10821074
printer.write(lines: namespaceInitCode)
10831075

10841076
let propertyAssignments = try generateNamespacePropertyAssignments(
10851077
data: data,
10861078
exportedSkeletons: exportedSkeletons,
1087-
namespaceBuilder: namespaceBuilder,
1088-
exposeToGlobal: exposeToGlobal
1079+
namespaceBuilder: namespaceBuilder
10891080
)
10901081
printer.write(lines: propertyAssignments)
10911082
}
@@ -1157,12 +1148,13 @@ struct BridgeJSLink {
11571148
private func generateNamespacePropertyAssignments(
11581149
data: LinkData,
11591150
exportedSkeletons: [ExportedSkeleton],
1160-
namespaceBuilder: NamespaceBuilder,
1161-
exposeToGlobal: Bool
1151+
namespaceBuilder: NamespaceBuilder
11621152
) throws -> [String] {
11631153
let printer = CodeFragmentPrinter()
11641154

1165-
if exposeToGlobal {
1155+
// Only include enum static assignments for modules with exposeToGlobal
1156+
let hasAnyGlobalExposure = exportedSkeletons.contains { $0.exposeToGlobal }
1157+
if hasAnyGlobalExposure {
11661158
printer.write(lines: data.enumStaticAssignments)
11671159
}
11681160

@@ -1182,10 +1174,8 @@ struct BridgeJSLink {
11821174
printer.write("};")
11831175
printer.write("_exports = exports;")
11841176

1185-
if exposeToGlobal {
1186-
let globalThisLines = namespaceBuilder.buildGlobalThisAssignments(exportedSkeletons: exportedSkeletons)
1187-
printer.write(lines: globalThisLines)
1188-
}
1177+
let globalThisLines = namespaceBuilder.buildGlobalThisAssignments(exportedSkeletons: exportedSkeletons)
1178+
printer.write(lines: globalThisLines)
11891179

11901180
printer.write("return exports;")
11911181

@@ -2243,20 +2233,21 @@ extension BridgeJSLink {
22432233
)
22442234
}
22452235

2246-
func buildNamespaceInitialization(exportedSkeletons: [ExportedSkeleton], exposeToGlobal: Bool) -> [String] {
2247-
guard exposeToGlobal else { return [] }
2248-
let allNamespacePaths = collectAllNamespacePaths(exportedSkeletons: exportedSkeletons)
2236+
func buildNamespaceInitialization(exportedSkeletons: [ExportedSkeleton]) -> [String] {
2237+
let globalSkeletons = exportedSkeletons.filter { $0.exposeToGlobal }
2238+
guard !globalSkeletons.isEmpty else { return [] }
2239+
let allNamespacePaths = collectAllNamespacePaths(exportedSkeletons: globalSkeletons)
22492240
return generateNamespaceInitializationCode(namespacePaths: allNamespacePaths)
22502241
}
22512242

22522243
func buildTopLevelNamespaceInitialization(
2253-
exportedSkeletons: [ExportedSkeleton],
2254-
exposeToGlobal: Bool
2244+
exportedSkeletons: [ExportedSkeleton]
22552245
) -> [String] {
2256-
guard exposeToGlobal else { return [] }
2246+
let globalSkeletons = exportedSkeletons.filter { $0.exposeToGlobal }
2247+
guard !globalSkeletons.isEmpty else { return [] }
22572248

22582249
var namespacedEnumPaths: Set<[String]> = []
2259-
for skeleton in exportedSkeletons {
2250+
for skeleton in globalSkeletons {
22602251
for enumDef in skeleton.enums where enumDef.namespace != nil && enumDef.enumType != .namespace {
22612252
namespacedEnumPaths.insert(enumDef.namespace!)
22622253
}
@@ -2267,7 +2258,7 @@ extension BridgeJSLink {
22672258
let printer = CodeFragmentPrinter()
22682259
printer.write(lines: initCode)
22692260

2270-
for skeleton in exportedSkeletons {
2261+
for skeleton in globalSkeletons {
22712262
for enumDef in skeleton.enums where enumDef.namespace != nil && enumDef.enumType != .namespace {
22722263
let namespacePath = enumDef.namespace!.joined(separator: ".")
22732264
printer.write("globalThis.\(namespacePath).\(enumDef.valuesName) = \(enumDef.valuesName);")
@@ -2280,7 +2271,7 @@ extension BridgeJSLink {
22802271
func buildGlobalThisAssignments(exportedSkeletons: [ExportedSkeleton]) -> [String] {
22812272
let printer = CodeFragmentPrinter()
22822273

2283-
for skeleton in exportedSkeletons {
2274+
for skeleton in exportedSkeletons where skeleton.exposeToGlobal {
22842275
for klass in skeleton.classes where klass.namespace != nil {
22852276
let namespacePath = klass.namespace!.joined(separator: ".")
22862277
printer.write("globalThis.\(namespacePath).\(klass.name) = exports.\(namespacePath).\(klass.name);")
@@ -2645,25 +2636,60 @@ extension BridgeJSLink {
26452636
/// - Returns: Array of TypeScript declaration lines defining the global namespace structure
26462637
func namespaceDeclarations(
26472638
exportedSkeletons: [ExportedSkeleton],
2648-
exposeToGlobal: Bool,
26492639
renderTSSignatureCallback: @escaping ([Parameter], BridgeType, Effects) -> String
26502640
) -> [String] {
26512641
let printer = CodeFragmentPrinter()
2652-
let rootNode = NamespaceNode(name: "")
2653-
2654-
buildExportsTree(rootNode: rootNode, exportedSkeletons: exportedSkeletons)
2655-
2656-
guard !rootNode.children.isEmpty else {
2657-
return printer.lines
2658-
}
2659-
2660-
if exposeToGlobal {
2661-
printer.write("export {};")
2662-
printer.nextLine()
2663-
printer.write("declare global {")
2664-
printer.indent()
2642+
2643+
let globalSkeletons = exportedSkeletons.filter { $0.exposeToGlobal }
2644+
let nonGlobalSkeletons = exportedSkeletons.filter { !$0.exposeToGlobal }
2645+
2646+
if !globalSkeletons.isEmpty {
2647+
let globalRootNode = NamespaceNode(name: "")
2648+
buildExportsTree(rootNode: globalRootNode, exportedSkeletons: globalSkeletons)
2649+
2650+
if !globalRootNode.children.isEmpty {
2651+
printer.write("export {};")
2652+
printer.nextLine()
2653+
printer.write("declare global {")
2654+
printer.indent()
2655+
generateNamespaceDeclarationsForNode(
2656+
node: globalRootNode,
2657+
depth: 1,
2658+
printer: printer,
2659+
exposeToGlobal: true,
2660+
renderTSSignatureCallback: renderTSSignatureCallback
2661+
)
2662+
printer.unindent()
2663+
printer.write("}")
2664+
printer.nextLine()
2665+
}
2666+
}
2667+
2668+
if !nonGlobalSkeletons.isEmpty {
2669+
let localRootNode = NamespaceNode(name: "")
2670+
buildExportsTree(rootNode: localRootNode, exportedSkeletons: nonGlobalSkeletons)
2671+
2672+
if !localRootNode.children.isEmpty {
2673+
generateNamespaceDeclarationsForNode(
2674+
node: localRootNode,
2675+
depth: 1,
2676+
printer: printer,
2677+
exposeToGlobal: false,
2678+
renderTSSignatureCallback: renderTSSignatureCallback
2679+
)
2680+
}
26652681
}
26662682

2683+
return printer.lines
2684+
}
2685+
2686+
private func generateNamespaceDeclarationsForNode(
2687+
node: NamespaceNode,
2688+
depth: Int,
2689+
printer: CodeFragmentPrinter,
2690+
exposeToGlobal: Bool,
2691+
renderTSSignatureCallback: @escaping ([Parameter], BridgeType, Effects) -> String
2692+
) {
26672693
func hasContent(node: NamespaceNode) -> Bool {
26682694
// Enums are always included
26692695
if !node.content.enums.isEmpty {
@@ -2845,22 +2871,14 @@ extension BridgeJSLink {
28452871
}
28462872
}
28472873

2848-
generateNamespaceDeclarations(node: childNode, depth: depth + 1)
2874+
generateNamespaceDeclarationsForNode(node: childNode, depth: depth + 1, printer: printer, exposeToGlobal: exposeToGlobal, renderTSSignatureCallback: renderTSSignatureCallback)
28492875

28502876
printer.unindent()
28512877
printer.write("}")
28522878
}
28532879
}
2854-
2855-
generateNamespaceDeclarations(node: rootNode, depth: 1)
2856-
2857-
if exposeToGlobal {
2858-
printer.unindent()
2859-
printer.write("}")
2860-
printer.nextLine()
2861-
}
2862-
2863-
return printer.lines
2880+
2881+
generateNamespaceDeclarations(node: node, depth: depth)
28642882
}
28652883
}
28662884

0 commit comments

Comments
 (0)