Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
41 changes: 26 additions & 15 deletions .taskfiles/desktop.yml
Original file line number Diff line number Diff line change
Expand Up @@ -31,52 +31,60 @@ tasks:
provisioner:
desc: "Build installer provisioner"
platforms: [windows]
dir: editor
cmds:
- node editor/scripts/build-provisioner.mjs
- node scripts/build-provisioner.mjs

dev:
desc: "Start Tauri desktop dev mode"
deps: [prepare]
ignore_error: true
dir: editor
cmds:
- cd editor && npx tauri dev --no-watch
- npx tauri dev --no-watch

build:
desc: "Build Tauri desktop app (production)"
deps: [prepare]
dir: editor
cmds:
- cd editor && npx tauri build
- npx tauri build

build:dev:
desc: "Build Tauri desktop app (dev, no bundling)"
deps: [prepare]
dir: editor
cmds:
- cd editor && npx tauri build --no-bundle
- npx tauri build --no-bundle

build:dev:mac:
desc: "Build Tauri desktop .app bundle (macOS)"
deps: [prepare]
dir: editor
cmds:
- cd editor && npx tauri build --bundles app
- npx tauri build --bundles app

build:dev:windows:
desc: "Build Tauri desktop NSIS installer (Windows)"
deps: [prepare]
dir: editor
cmds:
- cd editor && npx tauri build --bundles nsis
- npx tauri build --bundles nsis

build:dev:linux:
desc: "Build Tauri desktop AppImage (Linux)"
deps: [prepare]
dir: editor
cmds:
- cd editor && npx tauri build --bundles appimage
- npx tauri build --bundles appimage

clean:
desc: "Clean Tauri/Cargo build artifacts"
dir: editor
cmds:
- task: jlink:clean
- cd editor/src-tauri && cargo clean
- rm -rf editor/dist editor/build
- cd src-tauri && cargo clean
- rm -rf dist build

# ============================================================
# JLink — Build bundled Java runtime for Tauri
Expand Down Expand Up @@ -106,24 +114,26 @@ tasks:
jlink:runtime:
desc: "Create custom JRE with jlink"
deps: [jlink:jar]
dir: editor/src-tauri
cmds:
- rm -rf editor/src-tauri/runtime/jre
- mkdir -p editor/src-tauri/runtime
- rm -rf runtime/jre
- mkdir -p runtime
- >-
jlink
--add-modules {{.JLINK_MODULES}}
--strip-debug
--compress=zip-6
--no-header-files
--no-man-pages
--output editor/src-tauri/runtime/jre
--output runtime/jre
status:
- test -d editor/src-tauri/runtime/jre

jlink:clean:
desc: "Remove JLink runtime and bundled JARs"
dir: editor/src-tauri
cmds:
- rm -rf editor/src-tauri/libs editor/src-tauri/runtime
- rm -rf libs runtime

# macOS-only. Replaces jlink:runtime's single-arch JRE with a universal
# (arm64 + x86_64) one for the universal Tauri shell. Runs the x86_64
Expand All @@ -134,8 +144,9 @@ tasks:
desc: "Create universal (arm64+x86_64) JRE for the macOS Tauri build"
deps: [jlink:jar]
platforms: [darwin]
dir: editor
env:
JLINK_MODULES: "{{.JLINK_MODULES}}"
OUTPUT_DIR: editor/src-tauri/runtime/jre
OUTPUT_DIR: src-tauri/runtime/jre
cmds:
- editor/scripts/build-universal-mac-jre.sh
- scripts/build-universal-mac-jre.sh
20 changes: 12 additions & 8 deletions app/core/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -196,9 +196,13 @@ if (buildPrototypes) {
}
def frontendBuildTask = "frontend:build:${frontendMode}"

// Workspace root holds package.json and node_modules (shared across editor /
// future portal). Editor-specific paths (src, public, dist, tauri) live one
// level deeper under frontend/editor/. When the portal lands as an embedded
// app, add a sibling frontendPortalDir / frontendPortalDistDir alongside.
def frontendDir = file('../../frontend')
def frontendEditorDir = file('../../frontend/editor')
def frontendDistDir = file('../../frontend/editor/dist')
def frontendEditorDistDir = file('../../frontend/editor/dist')
def resourcesStaticDir = file('src/main/resources/static')
def generatedFrontendPaths = [
'assets',
Expand Down Expand Up @@ -263,13 +267,13 @@ tasks.register('npmBuild', Exec) {
doNotTrackState("Frontend build depends on untracked npmInstall task")
enabled = buildWithFrontend
group = 'frontend'
description = 'Build frontend application'
description = 'Build editor frontend application'
workingDir file('../..')
commandLine = ['task', frontendBuildTask]
inputs.dir(new File(frontendEditorDir, 'src'))
inputs.dir(new File(frontendEditorDir, 'public'))
inputs.file(new File(frontendDir, 'package.json'))
outputs.dir(frontendDistDir)
outputs.dir(frontendEditorDistDir)

// Show live output
standardOutput = System.out
Expand All @@ -280,25 +284,25 @@ tasks.register('npmBuild', Exec) {
environment 'VITE_API_BASE_URL', '/'

doFirst {
println "Building frontend application for production (mode=${frontendMode}, VITE_API_BASE_URL=/)"
println "Building editor frontend application for production (mode=${frontendMode}, VITE_API_BASE_URL=/)"
}
}

tasks.register('copyFrontendAssets', Copy) {
enabled = buildWithFrontend
group = 'frontend'
description = 'Copy frontend build to static resources'
description = 'Copy editor frontend build to static resources'
dependsOn npmBuild
dependsOn cleanFrontendAssets
from(frontendDistDir) {
from(frontendEditorDistDir) {
// Exclude files that conflict with backend static resources
exclude 'robots.txt' // Backend already has this
exclude 'favicon.ico' // Backend already has this
}
into resourcesStaticDir
duplicatesStrategy = DuplicatesStrategy.INCLUDE // Let frontend overwrite when needed
doFirst {
println "Copying frontend build from ${frontendDistDir} to ${resourcesStaticDir}..."
println "Copying frontend build from ${frontendEditorDistDir} to ${resourcesStaticDir}..."
println "Backend static resources will be preserved"
}
doLast {
Expand Down Expand Up @@ -330,7 +334,7 @@ tasks.named('copyFrontendAssets').configure {
}

if (buildWithFrontend) {
println "Frontend build enabled - JAR will include React frontend (mode=${frontendMode})"
println "Editor frontend build enabled - JAR will include React frontend (mode=${frontendMode})"
processResources.dependsOn copyFrontendAssets
} else {
println "Frontend build disabled - JAR will be backend-only with API landing page"
Expand Down
6 changes: 4 additions & 2 deletions frontend/.prettierignore
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
dist/
dist-portal/
editor/dist/
# Tauri/Cargo build output (binary assets named *.js etc. confuse Prettier)
editor/src-tauri/target/
# Tauri/Cargo build output (binary assets named *.js etc. confuse Prettier).
# Match nested target/ dirs too — provisioner/ and thumbnail-handler/ each
# have their own Cargo workspace under src-tauri/.
editor/src-tauri/**/target/
editor/src-tauri/gen/
node_modules/
editor/public/vendor/
Expand Down
17 changes: 12 additions & 5 deletions frontend/editor/scripts/setup-env.mts
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,18 @@
* Vite automatically layers these `.local` files on top of the committed ones.
*
* Usage:
* tsx scripts/setup-env.ts # ensures .env.local
* tsx scripts/setup-env.ts --desktop # also ensures .env.desktop.local
* tsx scripts/setup-env.ts --saas # also ensures .env.saas.local
* tsx scripts/setup-env.mts # ensures .env.local
* tsx scripts/setup-env.mts --desktop # also ensures .env.desktop.local
* tsx scripts/setup-env.mts --saas # also ensures .env.saas.local
*
* Why .mts (and not .ts)?
* This script needs `import.meta.url` to resolve paths relative to itself,
* because Task invokes it from the workspace root (frontend/) but the .env
* files live one level deeper at frontend/editor/. `import.meta` is only
* valid in ESM output; `editor/scripts/tsconfig.json` extends the editor
* tsconfig which uses `module: node16`, treating plain .ts as CommonJS
* (TS1470 error on `import.meta`). The .mts extension explicitly marks
* the file as ESM, which tsx already runs at runtime anyway.
*/

import { existsSync, writeFileSync } from "fs";
Expand All @@ -17,8 +26,6 @@ import { fileURLToPath } from "url";

// .env files live next to the editor's vite.config.ts (frontend/editor/).
// Resolve relative to this script regardless of where the build was invoked.
// `import.meta.dirname` would be tidier but isn't available under tsx's CJS
// transpilation today, so go via fileURLToPath for portability.
const scriptDir = dirname(fileURLToPath(import.meta.url));
const root = resolve(scriptDir, "..");
const args = process.argv.slice(2);
Expand Down
3 changes: 2 additions & 1 deletion frontend/eslint.config.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,8 @@ import tseslint from "typescript-eslint";

const srcGlobs = ["editor/src/**/*.{js,mjs,jsx,ts,tsx}"];
const nodeGlobs = [
"editor/scripts/**/*.{js,ts,mjs}",
"scripts/**/*.{js,ts,mjs,mts}",
"editor/scripts/**/*.{js,ts,mjs,mts}",
"editor/*.config.{js,ts,mjs}",
"*.config.{js,ts,mjs}",
];
Expand Down
2 changes: 1 addition & 1 deletion frontend/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -82,7 +82,7 @@
"web-vitals": "^5.1.0"
},
"scripts": {
"update:minor": "node editor/scripts/update-minor.js",
"update:minor": "node scripts/update-minor.js",
"update:major": "npx npm-check-updates -u && npm install",
"update:interactive": "npx npm-check-updates -i",
"update:minor-strict": "npx npm-check-updates -u --target minor && npm install"
Expand Down
Loading