Skip to content

Commit 7f93a62

Browse files
committed
Reorganize build: SwiftKit has "swift kit" core, and SwiftKitExample
Further progress on cleaning up the build. We're still having issues with various runtime issues but this gets us to a more understandable separation of "what is a sample" and "what is the library". There's more to be done before we can kill off `make` but this does quite some progress. - Sample apps "anything with a main()" have their own place; it used to be very mixed up in the same target; together with the example lib - `JavaKitSampleApp` there's a sample for javakit which uses the `JavaKitExample` defined swift type - `SwiftKitSampleApp` the jextract demo app, uses the `ExampleSwiftLibrary` - those JavaKitExample and ExampleSwiftLibrary could use further moving out of `Sources/...` as they're example stuff, not "the library" but I leave at this for now... Running samples: ./gradlew Samples:SwiftKitSampleApp:run (Samples:Name:run) - `./gradlew test` does the jextract and whatever the sample apps need - make is still around; didn't hook up any of the javakit generation - generated sources no longer in wrong directory; `src/generated/`... as the usual convention in Java land (and not committed)
1 parent a64f805 commit 7f93a62

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

41 files changed

+480
-296
lines changed

.github/workflows/pull_request.yml

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -41,11 +41,8 @@ jobs:
4141
# distribution: 'zulu'
4242
# java-version: '22'
4343
# cache: 'gradle'
44-
- name: Generate sources (make) (Temporary)
45-
# TODO: this should be triggered by the respective builds
46-
run: make jextract-run
4744
- name: Gradle build
48-
run: ./gradlew build --no-daemon
45+
run: ./gradlew build --info --no-daemon
4946

5047
test-swift:
5148
name: Swift tests (swift:${{ matrix.swift_version }} jdk:${{matrix.jdk_vendor}} os:${{ matrix.os_version }})

.gitignore

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,10 +9,15 @@ DerivedData/
99
.netrc
1010
*.class
1111
bin/
12+
BuildLogic/out/
1213

1314
# Ignore gradle build artifacts
1415
.gradle
1516
**/build/
17+
lib/
18+
19+
# Ignore package resolved
20+
Package.resolved
1621

1722
# Avoid ignoring Gradle wrapper jar file (.jar files are usually ignored)
1823
!gradle-wrapper.jar
@@ -24,4 +29,4 @@ bin/
2429
.gradletasknamecache
2530

2631
# Ignore generated sources
27-
JavaSwiftKitDemo/src/main/java/com/example/swift/generated/*
32+
**/generated/

BuildLogic/src/main/kotlin/build-logic.java-common-conventions.gradle.kts

Lines changed: 40 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,8 @@
1212
//
1313
//===----------------------------------------------------------------------===//
1414

15+
import java.util.*
16+
1517
plugins {
1618
java
1719
}
@@ -40,16 +42,39 @@ tasks.withType(JavaCompile::class).forEach {
4042
it.options.compilerArgs.add("-Xlint:preview")
4143
}
4244

45+
46+
fun javaLibraryPaths(): List<String> {
47+
val osName = System.getProperty("os.name")
48+
val osArch = System.getProperty("os.arch")
49+
val isLinux = osName.lowercase(Locale.getDefault()).contains("linux")
50+
51+
return listOf(
52+
if (osName.lowercase(Locale.getDefault()).contains("linux")) {
53+
"""$rootDir/.build/$osArch-unknown-linux-gnu/debug/"""
54+
} else {
55+
if (osArch.equals("aarch64")) {
56+
"""$rootDir/.build/arm64-apple-macosx/debug/"""
57+
} else {
58+
"""$rootDir/.build/$osArch-apple-macosx/debug/"""
59+
}
60+
},
61+
if (isLinux) {
62+
"/usr/lib/swift/linux"
63+
} else {
64+
// assume macOS
65+
"/usr/lib/swift/"
66+
}
67+
)
68+
}
69+
70+
4371
// Configure paths for native (Swift) libraries
4472
tasks.test {
4573
jvmArgs(
4674
"--enable-native-access=ALL-UNNAMED",
4775

4876
// Include the library paths where our dylibs are that we want to load and call
49-
"-Djava.library.path=" + listOf(
50-
"""$rootDir/.build/arm64-apple-macosx/debug/""",
51-
"/usr/lib/swift/"
52-
).joinToString(File.pathSeparator)
77+
"-Djava.library.path=" + javaLibraryPaths().joinToString(File.pathSeparator)
5378
)
5479
}
5580

@@ -60,14 +85,15 @@ tasks.withType<Test> {
6085
}
6186

6287

63-
val buildSwiftJExtract = tasks.register<Exec>("buildSwiftJExtract") {
64-
description = "Builds Swift targets, including jextract-swift"
65-
66-
workingDir("..")
67-
commandLine("make")
68-
}
69-
70-
tasks.build {
71-
dependsOn(buildSwiftJExtract)
72-
}
88+
// TODO: This is a crude workaround, we'll remove 'make' soon and properly track build dependencies
89+
// val buildSwiftJExtract = tasks.register<Exec>("buildMake") {
90+
// description = "Triggers 'make' build"
91+
//
92+
// workingDir(rootDir)
93+
// commandLine("make")
94+
// }
95+
//
96+
// tasks.build {
97+
// dependsOn(buildSwiftJExtract)
98+
// }
7399

Makefile

Lines changed: 17 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -37,17 +37,15 @@ BUILD_DIR := .build/$(ARCH_SUBDIR)-apple-macosx
3737
LIB_SUFFIX := dylib
3838
endif
3939

40+
SAMPLES_DIR := "Samples"
4041

4142
all: generate-all
4243

43-
$(BUILD_DIR)/debug/libJavaKit.$(LIB_SUFFIX) $(BUILD_DIR)/debug/libJavaKitExample.$(LIB_SUFFIX) $(BUILD_DIR)/debug/Java2Swift:
44+
$(BUILD_DIR)/debug/libJavaKit.$(LIB_SUFFIX) $(BUILD_DIR)/debug/Java2Swift:
4445
swift build
4546

46-
./JavaSwiftKitDemo/build/classes/java/main/com/example/swift/HelloSubclass.class: JavaSwiftKitDemo/src/main/java/com/example/swift
47-
./gradlew build
48-
49-
run: $(BUILD_DIR)/debug/libJavaKit.$(LIB_SUFFIX) $(BUILD_DIR)/debug/libJavaKitExample.$(LIB_SUFFIX) JavaSwiftKitDemo/src/main/java/com/example/swift
50-
java -cp JavaSwiftKitDemo/build/classes/java/main -Djava.library.path=$(BUILD_DIR)/debug/ com.example.swift.HelloSwift
47+
run: $(BUILD_DIR)/debug/libJavaKit.$(LIB_SUFFIX) $(BUILD_DIR)/debug/libExampleSwiftLibrary.$(LIB_SUFFIX)
48+
./gradlew Samples:JavaKitSampleApp:run
5149

5250
Java2Swift: $(BUILD_DIR)/debug/Java2Swift
5351

@@ -70,7 +68,8 @@ generate-JavaKitNetwork: Java2Swift generate-JavaKit
7068
generate-all: generate-JavaKit generate-JavaKitReflection generate-JavaKitJar generate-JavaKitNetwork \
7169
jextract-swift
7270
clean:
73-
rm -rf .build
71+
rm -rf .build; \
72+
rm -rf Samples/SwiftKitExampleApp/src/generated/java/*
7473

7574
format:
7675
swift format --recursive . -i
@@ -81,7 +80,6 @@ format:
8180

8281
JEXTRACT_BUILD_DIR="$(BUILD_DIR)/jextract"
8382

84-
# Parameter: Swift source file
8583
define make_swiftinterface
8684
$(eval $@_MODULE = $(1))
8785
$(eval $@_FILENAME = $(2))
@@ -99,17 +97,21 @@ jextract-swift: generate-JExtract-interface-files
9997

10098
generate-JExtract-interface-files: $(BUILD_DIR)/debug/libJavaKit.$(LIB_SUFFIX)
10199
echo "Generate .swiftinterface files..."
102-
@$(call make_swiftinterface, "JavaKitExample", "MySwiftLibrary")
103-
@$(call make_swiftinterface, "JavaKitExample", "SwiftKit")
100+
@$(call make_swiftinterface, "ExampleSwiftLibrary", "MySwiftLibrary")
101+
@$(call make_swiftinterface, "SwiftKitSwift", "SwiftKit")
104102

105103
jextract-run: jextract-swift generate-JExtract-interface-files
106104
swift run jextract-swift \
107105
--package-name com.example.swift.generated \
108-
--swift-module JavaKitExample \
109-
--output-directory JavaSwiftKitDemo/src/main/java \
110-
$(BUILD_DIR)/jextract/JavaKitExample/MySwiftLibrary.swiftinterface \
111-
$(BUILD_DIR)/jextract/JavaKitExample/SwiftKit.swiftinterface
106+
--swift-module ExampleSwiftLibrary \
107+
--output-directory ${SAMPLES_DIR}/SwiftKitSampleApp/src/generated/java \
108+
$(BUILD_DIR)/jextract/ExampleSwiftLibrary/MySwiftLibrary.swiftinterface; \
109+
swift run jextract-swift \
110+
--package-name org.swift.swiftkit.generated \
111+
--swift-module SwiftKitSwift \
112+
--output-directory ${SAMPLES_DIR}/SwiftKitSampleApp/src/generated/java \
113+
$(BUILD_DIR)/jextract/SwiftKitSwift/SwiftKit.swiftinterface
112114

113115

114116
jextract-run-java: jextract-swift generate-JExtract-interface-files
115-
./gradlew run
117+
./gradlew Samples:SwiftKitSampleApp:run

Package.resolved

Lines changed: 0 additions & 32 deletions
This file was deleted.

Package.swift

Lines changed: 47 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ func findJavaHome() -> String {
1818
// This is a workaround for envs (some IDEs) which have trouble with
1919
// picking up env variables during the build process
2020
let path = "\(FileManager.default.homeDirectoryForCurrentUser.path()).java_home"
21-
if let home = try? String(contentsOfFile: path) {
21+
if let home = try? String(contentsOfFile: path, encoding: .utf8) {
2222
if let lastChar = home.last, lastChar.isNewline {
2323
return String(home.dropLast())
2424
}
@@ -36,8 +36,8 @@ let javaIncludePath = "\(javaHome)/include"
3636
#elseif os(macOS)
3737
let javaPlatformIncludePath = "\(javaIncludePath)/darwin"
3838
#else
39+
// TODO: Handle windows as well
3940
#error("Currently only macOS and Linux platforms are supported, this may change in the future.")
40-
// TODO: Handle windows as well
4141
#endif
4242

4343
let package = Package(
@@ -50,6 +50,7 @@ let package = Package(
5050
.macCatalyst(.v13),
5151
],
5252
products: [
53+
// ==== JavaKit (i.e. calling Java directly Swift utilities)
5354
.library(
5455
name: "JavaKit",
5556
targets: ["JavaKit"]
@@ -70,12 +71,6 @@ let package = Package(
7071
targets: ["JavaKitReflection"]
7172
),
7273

73-
.library(
74-
name: "JavaKitExample",
75-
type: .dynamic,
76-
targets: ["JavaKitExample"]
77-
),
78-
7974
.library(
8075
name: "JavaKitVM",
8176
targets: ["JavaKitVM"]
@@ -86,20 +81,43 @@ let package = Package(
8681
targets: ["JavaTypes"]
8782
),
8883

89-
.library(
90-
name: "JExtractSwift",
91-
targets: ["JExtractSwift"]
92-
),
93-
9484
.executable(
9585
name: "Java2Swift",
9686
targets: ["Java2Swift"]
9787
),
9888

89+
// ==== jextract-swift (extract Java accessors from Swift interface files)
90+
9991
.executable(
10092
name: "jextract-swift",
10193
targets: ["JExtractSwiftTool"]
10294
),
95+
96+
// Support library written in Swift for SwiftKit "Java"
97+
.library(
98+
name: "SwiftKitSwift",
99+
type: .dynamic,
100+
targets: ["SwiftKitSwift"]
101+
),
102+
103+
.library(
104+
name: "JExtractSwift",
105+
targets: ["JExtractSwift"]
106+
),
107+
108+
// ==== Examples
109+
110+
.library(
111+
name: "JavaKitExample",
112+
type: .dynamic,
113+
targets: ["JavaKitExample"]
114+
),
115+
.library(
116+
name: "ExampleSwiftLibrary",
117+
type: .dynamic,
118+
targets: ["ExampleSwiftLibrary"]
119+
),
120+
103121
],
104122
dependencies: [
105123
.package(url: "https://github.com/swiftlang/swift-syntax.git", branch: "main"),
@@ -187,6 +205,22 @@ let package = Package(
187205
.unsafeFlags(["-I\(javaIncludePath)", "-I\(javaPlatformIncludePath)"])
188206
]
189207
),
208+
.target(
209+
name: "ExampleSwiftLibrary",
210+
dependencies: [],
211+
swiftSettings: [
212+
.swiftLanguageMode(.v5),
213+
.unsafeFlags(["-I\(javaIncludePath)", "-I\(javaPlatformIncludePath)"])
214+
]
215+
),
216+
.target(
217+
name: "SwiftKitSwift",
218+
dependencies: [],
219+
swiftSettings: [
220+
.swiftLanguageMode(.v5),
221+
.unsafeFlags(["-I\(javaIncludePath)", "-I\(javaPlatformIncludePath)"])
222+
]
223+
),
190224

191225
.target(
192226
name: "JavaRuntime",

JavaSwiftKitDemo/build.gradle.kts renamed to Samples/JavaKitSampleApp/build.gradle

Lines changed: 11 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,8 @@
1212
//
1313
//===----------------------------------------------------------------------===//
1414

15+
import org.swift.swiftkit.gradle.BuildUtils
16+
1517
plugins {
1618
id("build-logic.java-application-conventions")
1719
}
@@ -30,6 +32,8 @@ java {
3032
}
3133

3234
dependencies {
35+
implementation(project(':SwiftKit'))
36+
3337
testImplementation(platform("org.junit:junit-bom:5.10.0"))
3438
testImplementation("org.junit.jupiter:junit-jupiter")
3539
}
@@ -39,25 +43,18 @@ tasks.test {
3943
}
4044

4145
application {
42-
mainClass = "org.example.HelloJava2Swift"
46+
mainClass = "com.example.swift.JavaKitSampleMain"
4347

4448
// In order to silence:
4549
// WARNING: A restricted method in java.lang.foreign.SymbolLookup has been called
4650
// WARNING: java.lang.foreign.SymbolLookup::libraryLookup has been called by org.example.swift.JavaKitExample in an unnamed module
4751
// WARNING: Use --enable-native-access=ALL-UNNAMED to avoid a warning for callers in this module
4852
// WARNING: Restricted methods will be blocked in a future release unless native access is enabled
4953
// FIXME: Find out the proper solution to this
50-
applicationDefaultJvmArgs = listOf(
51-
"--enable-native-access=ALL-UNNAMED",
52-
53-
// Include the library paths where our dylibs are that we want to load and call
54-
"-Djava.library.path=" + listOf(
55-
"""$rootDir/.build/arm64-apple-macosx/debug/""",
56-
"/usr/lib/swift/"
57-
).joinToString(":"),
58-
59-
// Enable tracing downcalls (to Swift)
60-
"-Djextract.trace.downcalls=true"
61-
)
62-
}
54+
applicationDefaultJvmArgs = [
55+
"--enable-native-access=ALL-UNNAMED",
6356

57+
// Include the library paths where our dylibs are that we want to load and call
58+
"-Djava.library.path=" + BuildUtils.javaLibraryPaths(rootDir).join(":")
59+
]
60+
}

JavaSwiftKitDemo/src/main/java/com/example/swift/HelloSubclass.java renamed to Samples/JavaKitSampleApp/src/main/java/com/example/swift/HelloSubclass.java

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,8 +14,6 @@
1414

1515
package com.example.swift;
1616

17-
import com.example.swift.HelloSwift;
18-
1917
public class HelloSubclass extends HelloSwift {
2018
private String greeting;
2119

0 commit comments

Comments
 (0)