@jetstart/core 2.3.1 → 2.3.3
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.
- package/dist/build/dex-generator.js +12 -5
- package/dist/build/gradle.js +10 -7
- package/dist/build/kotlin-compiler.d.ts +7 -0
- package/dist/build/kotlin-compiler.js +88 -16
- package/package.json +3 -3
- package/src/build/dex-generator.ts +12 -5
- package/src/build/gradle.ts +10 -10
- package/src/build/kotlin-compiler.ts +102 -17
|
@@ -52,14 +52,21 @@ class DexGenerator {
|
|
|
52
52
|
async findD8() {
|
|
53
53
|
if (this.d8Path)
|
|
54
54
|
return this.d8Path;
|
|
55
|
-
// Check
|
|
56
|
-
|
|
57
|
-
|
|
55
|
+
// Check environment variables first, but validate the path actually exists
|
|
56
|
+
const envAndroidHome = process.env.ANDROID_HOME || process.env.ANDROID_SDK_ROOT;
|
|
57
|
+
let androidHome;
|
|
58
|
+
if (envAndroidHome && fs.existsSync(path.join(envAndroidHome, 'build-tools'))) {
|
|
59
|
+
androidHome = envAndroidHome;
|
|
60
|
+
}
|
|
61
|
+
// Fallback: probe common install locations
|
|
58
62
|
if (!androidHome) {
|
|
59
63
|
const commonLocations = [
|
|
60
|
-
'C:\\Android',
|
|
61
64
|
path.join(os.homedir(), 'AppData', 'Local', 'Android', 'Sdk'),
|
|
65
|
+
'C:\\Android',
|
|
62
66
|
'C:\\Users\\Public\\Android\\Sdk',
|
|
67
|
+
path.join(os.homedir(), 'Android', 'Sdk'),
|
|
68
|
+
path.join(os.homedir(), 'Library', 'Android', 'sdk'),
|
|
69
|
+
'/opt/android-sdk',
|
|
63
70
|
];
|
|
64
71
|
for (const loc of commonLocations) {
|
|
65
72
|
if (fs.existsSync(path.join(loc, 'build-tools'))) {
|
|
@@ -70,7 +77,7 @@ class DexGenerator {
|
|
|
70
77
|
}
|
|
71
78
|
}
|
|
72
79
|
if (!androidHome) {
|
|
73
|
-
(0, logger_1.error)('
|
|
80
|
+
(0, logger_1.error)('Android build-tools not found');
|
|
74
81
|
return null;
|
|
75
82
|
}
|
|
76
83
|
// d8 is in build-tools
|
package/dist/build/gradle.js
CHANGED
|
@@ -42,6 +42,7 @@ const child_process_1 = require("child_process");
|
|
|
42
42
|
const fs = __importStar(require("fs"));
|
|
43
43
|
const path = __importStar(require("path"));
|
|
44
44
|
const os = __importStar(require("os"));
|
|
45
|
+
const shared_1 = require("@jetstart/shared");
|
|
45
46
|
const parser_1 = require("./parser");
|
|
46
47
|
/**
|
|
47
48
|
* ADB Helper for auto-installing APKs
|
|
@@ -288,16 +289,18 @@ class GradleExecutor {
|
|
|
288
289
|
async execute(config) {
|
|
289
290
|
const startTime = Date.now();
|
|
290
291
|
const gradlePath = this.findGradle(config.projectPath);
|
|
291
|
-
// If Gradle not found,
|
|
292
|
+
// If Gradle not found, fail build with clear error
|
|
292
293
|
if (!gradlePath) {
|
|
293
|
-
console.log('[Gradle] No Gradle found, returning mock successful build for testing');
|
|
294
|
-
// Simulate build delay
|
|
295
|
-
await new Promise(resolve => setTimeout(resolve, 2000));
|
|
296
294
|
return {
|
|
297
|
-
success:
|
|
295
|
+
success: false,
|
|
298
296
|
buildTime: Date.now() - startTime,
|
|
299
|
-
|
|
300
|
-
|
|
297
|
+
errors: [{
|
|
298
|
+
file: 'gradle',
|
|
299
|
+
line: 0,
|
|
300
|
+
column: 0,
|
|
301
|
+
message: 'Gradle not found. Please install Gradle 8.0+ or ensure the Gradle wrapper (gradlew) exists in your project project.',
|
|
302
|
+
severity: shared_1.ErrorSeverity.ERROR
|
|
303
|
+
}]
|
|
301
304
|
};
|
|
302
305
|
}
|
|
303
306
|
// Ensure Android SDK is configured
|
|
@@ -22,6 +22,13 @@ export declare class KotlinCompiler {
|
|
|
22
22
|
findComposeCompiler(): Promise<string | null>;
|
|
23
23
|
/**
|
|
24
24
|
* Find kotlinc executable
|
|
25
|
+
*
|
|
26
|
+
* Search order:
|
|
27
|
+
* 1. KOTLIN_HOME env var (set in .env or shell)
|
|
28
|
+
* 2. ANDROID_STUDIO_HOME env var
|
|
29
|
+
* 3. Platform-specific static paths (Scoop, Chocolatey, SDKMAN, snap, …)
|
|
30
|
+
* 4. Versioned IDE directories (IntelliJ IDEA, JetBrains Toolbox, Android Studio)
|
|
31
|
+
* 5. `where` / `which` fallback
|
|
25
32
|
*/
|
|
26
33
|
findKotlinc(): Promise<string | null>;
|
|
27
34
|
/**
|
|
@@ -102,27 +102,99 @@ class KotlinCompiler {
|
|
|
102
102
|
}
|
|
103
103
|
/**
|
|
104
104
|
* Find kotlinc executable
|
|
105
|
+
*
|
|
106
|
+
* Search order:
|
|
107
|
+
* 1. KOTLIN_HOME env var (set in .env or shell)
|
|
108
|
+
* 2. ANDROID_STUDIO_HOME env var
|
|
109
|
+
* 3. Platform-specific static paths (Scoop, Chocolatey, SDKMAN, snap, …)
|
|
110
|
+
* 4. Versioned IDE directories (IntelliJ IDEA, JetBrains Toolbox, Android Studio)
|
|
111
|
+
* 5. `where` / `which` fallback
|
|
105
112
|
*/
|
|
106
113
|
async findKotlinc() {
|
|
107
114
|
if (this.kotlincPath)
|
|
108
115
|
return this.kotlincPath;
|
|
109
|
-
|
|
116
|
+
const win = os.platform() === 'win32';
|
|
117
|
+
const localAppData = process.env.LOCALAPPDATA || path.join(os.homedir(), 'AppData', 'Local');
|
|
118
|
+
const progFiles = process.env.PROGRAMFILES || 'C:\\Program Files';
|
|
119
|
+
/**
|
|
120
|
+
* Scan `parentDir` for subdirectories whose names start with `entryPrefix`
|
|
121
|
+
* (pass '' to accept any entry), then return the first candidate that exists:
|
|
122
|
+
* path.join(parentDir, entry, ...rest)
|
|
123
|
+
* Entries are sorted descending so the latest version is tried first.
|
|
124
|
+
* Returns null (never throws) if the directory is missing or unreadable.
|
|
125
|
+
*/
|
|
126
|
+
const findInVersionedDir = (parentDir, entryPrefix, ...rest) => {
|
|
127
|
+
try {
|
|
128
|
+
if (!fs.existsSync(parentDir))
|
|
129
|
+
return null;
|
|
130
|
+
const entries = fs.readdirSync(parentDir)
|
|
131
|
+
.filter(e => !entryPrefix || e.toLowerCase().startsWith(entryPrefix.toLowerCase()))
|
|
132
|
+
.sort()
|
|
133
|
+
.reverse(); // latest version first
|
|
134
|
+
for (const entry of entries) {
|
|
135
|
+
const candidate = path.join(parentDir, entry, ...rest);
|
|
136
|
+
if (fs.existsSync(candidate))
|
|
137
|
+
return candidate;
|
|
138
|
+
}
|
|
139
|
+
}
|
|
140
|
+
catch { /* permission / access errors — silently skip */ }
|
|
141
|
+
return null;
|
|
142
|
+
};
|
|
143
|
+
const homeDir = os.homedir();
|
|
144
|
+
// JetStart installs kotlinc here when the user runs --full-install
|
|
145
|
+
const jetstartKotlinc = win
|
|
146
|
+
? path.join(homeDir, '.jetstart', 'kotlinc', 'bin', 'kotlinc.bat')
|
|
147
|
+
: path.join(homeDir, '.jetstart', 'kotlinc', 'bin', 'kotlinc');
|
|
148
|
+
// Validate KOTLIN_HOME if set — only use it when it actually points to kotlinc
|
|
149
|
+
const kotlinHomeCandidate = process.env.KOTLIN_HOME
|
|
150
|
+
? (win
|
|
151
|
+
? path.join(process.env.KOTLIN_HOME, 'bin', 'kotlinc.bat')
|
|
152
|
+
: path.join(process.env.KOTLIN_HOME, 'bin', 'kotlinc'))
|
|
153
|
+
: null;
|
|
110
154
|
const locations = [
|
|
111
|
-
//
|
|
112
|
-
|
|
113
|
-
//
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
//
|
|
119
|
-
'
|
|
120
|
-
'
|
|
121
|
-
//
|
|
122
|
-
'
|
|
123
|
-
|
|
155
|
+
// JetStart managed install (~/.jetstart/kotlinc) — checked first
|
|
156
|
+
jetstartKotlinc,
|
|
157
|
+
// env overrides (validated)
|
|
158
|
+
kotlinHomeCandidate,
|
|
159
|
+
process.env.ANDROID_STUDIO_HOME
|
|
160
|
+
? path.join(process.env.ANDROID_STUDIO_HOME, 'plugins', 'Kotlin', 'kotlinc', 'bin', 'kotlinc')
|
|
161
|
+
: null,
|
|
162
|
+
// Windows static paths
|
|
163
|
+
win ? path.join(progFiles, 'kotlinc', 'bin', 'kotlinc.bat') : null,
|
|
164
|
+
win ? 'C:\\kotlinc\\bin\\kotlinc.bat' : null,
|
|
165
|
+
// Scoop (~\scoop\apps\kotlin\current)
|
|
166
|
+
win ? path.join(homeDir, 'scoop', 'apps', 'kotlin', 'current', 'bin', 'kotlinc.bat') : null,
|
|
167
|
+
// Chocolatey
|
|
168
|
+
win ? 'C:\\ProgramData\\chocolatey\\bin\\kotlinc.bat' : null,
|
|
169
|
+
// Android Studio — standard Google installer
|
|
170
|
+
win ? path.join(progFiles, 'Android', 'Android Studio', 'plugins', 'Kotlin', 'kotlinc', 'bin', 'kotlinc.bat') : null,
|
|
171
|
+
win ? path.join(localAppData, 'Programs', 'Android Studio', 'plugins', 'Kotlin', 'kotlinc', 'bin', 'kotlinc.bat') : null,
|
|
172
|
+
// Windows versioned IDE paths (wildcard scan)
|
|
173
|
+
// IntelliJ IDEA — any version under C:\Program Files\JetBrains
|
|
174
|
+
win ? findInVersionedDir(path.join(progFiles, 'JetBrains'), 'IntelliJ IDEA', 'plugins', 'Kotlin', 'kotlinc', 'bin', 'kotlinc.bat') : null,
|
|
175
|
+
// JetBrains Toolbox — IDEA Ultimate
|
|
176
|
+
win ? findInVersionedDir(path.join(localAppData, 'JetBrains', 'Toolbox', 'apps', 'IDEA-U', 'ch-0'), '', 'plugins', 'Kotlin', 'kotlinc', 'bin', 'kotlinc.bat') : null,
|
|
177
|
+
// JetBrains Toolbox — IDEA Community
|
|
178
|
+
win ? findInVersionedDir(path.join(localAppData, 'JetBrains', 'Toolbox', 'apps', 'IDEA-C', 'ch-0'), '', 'plugins', 'Kotlin', 'kotlinc', 'bin', 'kotlinc.bat') : null,
|
|
179
|
+
// JetBrains Toolbox — Android Studio (Jellyfish+)
|
|
180
|
+
win ? findInVersionedDir(path.join(localAppData, 'JetBrains', 'Toolbox', 'apps', 'AndroidStudio', 'ch-0'), '', 'plugins', 'Kotlin', 'kotlinc', 'bin', 'kotlinc.bat') : null,
|
|
181
|
+
// Unix / macOS static paths
|
|
182
|
+
!win ? '/usr/local/bin/kotlinc' : null,
|
|
183
|
+
!win ? '/usr/bin/kotlinc' : null,
|
|
184
|
+
// Homebrew (Apple Silicon + Intel)
|
|
185
|
+
!win ? '/opt/homebrew/bin/kotlinc' : null,
|
|
186
|
+
!win ? '/usr/local/opt/kotlin/bin/kotlinc' : null,
|
|
187
|
+
// SDKMAN (~/.sdkman/candidates/kotlin/current)
|
|
188
|
+
!win ? path.join(homeDir, '.sdkman', 'candidates', 'kotlin', 'current', 'bin', 'kotlinc') : null,
|
|
189
|
+
// Snap
|
|
190
|
+
!win ? '/snap/bin/kotlinc' : null,
|
|
191
|
+
// IntelliJ IDEA — Linux Toolbox
|
|
192
|
+
!win ? findInVersionedDir(path.join(homeDir, '.local', 'share', 'JetBrains', 'Toolbox', 'apps', 'IDEA-U', 'ch-0'), '', 'plugins', 'Kotlin', 'kotlinc', 'bin', 'kotlinc') : null,
|
|
193
|
+
];
|
|
124
194
|
for (const loc of locations) {
|
|
125
|
-
|
|
195
|
+
if (!loc)
|
|
196
|
+
continue;
|
|
197
|
+
const execPath = win && !loc.endsWith('.bat') ? `${loc}.bat` : loc;
|
|
126
198
|
if (fs.existsSync(execPath)) {
|
|
127
199
|
this.kotlincPath = execPath;
|
|
128
200
|
(0, logger_1.log)(`Found kotlinc at: ${execPath}`);
|
|
@@ -131,7 +203,7 @@ class KotlinCompiler {
|
|
|
131
203
|
}
|
|
132
204
|
// Try to find via 'where' (Windows) or 'which' (Unix)
|
|
133
205
|
try {
|
|
134
|
-
const cmd =
|
|
206
|
+
const cmd = win ? 'where' : 'which';
|
|
135
207
|
const result = await this.runCommand(cmd, ['kotlinc']);
|
|
136
208
|
if (result.success && result.stdout.trim()) {
|
|
137
209
|
this.kotlincPath = result.stdout.trim().split('\n')[0];
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@jetstart/core",
|
|
3
|
-
"version": "2.3.
|
|
3
|
+
"version": "2.3.3",
|
|
4
4
|
"description": "Build server and orchestration for JetStart",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"types": "dist/index.d.ts",
|
|
@@ -33,8 +33,8 @@
|
|
|
33
33
|
},
|
|
34
34
|
"homepage": "https://github.com/dev-phantom/jetstart#readme",
|
|
35
35
|
"dependencies": {
|
|
36
|
-
"@jetstart/shared": "^2.3.
|
|
37
|
-
"@jetstart/logs": "^2.3.
|
|
36
|
+
"@jetstart/shared": "^2.3.3",
|
|
37
|
+
"@jetstart/logs": "^2.3.3",
|
|
38
38
|
"express": "^4.18.2",
|
|
39
39
|
"ws": "^8.14.2",
|
|
40
40
|
"chokidar": "^3.5.3",
|
|
@@ -26,15 +26,22 @@ export class DexGenerator {
|
|
|
26
26
|
async findD8(): Promise<string | null> {
|
|
27
27
|
if (this.d8Path) return this.d8Path;
|
|
28
28
|
|
|
29
|
-
// Check
|
|
30
|
-
|
|
29
|
+
// Check environment variables first, but validate the path actually exists
|
|
30
|
+
const envAndroidHome = process.env.ANDROID_HOME || process.env.ANDROID_SDK_ROOT;
|
|
31
|
+
let androidHome: string | undefined;
|
|
32
|
+
if (envAndroidHome && fs.existsSync(path.join(envAndroidHome, 'build-tools'))) {
|
|
33
|
+
androidHome = envAndroidHome;
|
|
34
|
+
}
|
|
31
35
|
|
|
32
|
-
// Fallback
|
|
36
|
+
// Fallback: probe common install locations
|
|
33
37
|
if (!androidHome) {
|
|
34
38
|
const commonLocations = [
|
|
35
|
-
'C:\\Android',
|
|
36
39
|
path.join(os.homedir(), 'AppData', 'Local', 'Android', 'Sdk'),
|
|
40
|
+
'C:\\Android',
|
|
37
41
|
'C:\\Users\\Public\\Android\\Sdk',
|
|
42
|
+
path.join(os.homedir(), 'Android', 'Sdk'),
|
|
43
|
+
path.join(os.homedir(), 'Library', 'Android', 'sdk'),
|
|
44
|
+
'/opt/android-sdk',
|
|
38
45
|
];
|
|
39
46
|
for (const loc of commonLocations) {
|
|
40
47
|
if (fs.existsSync(path.join(loc, 'build-tools'))) {
|
|
@@ -46,7 +53,7 @@ export class DexGenerator {
|
|
|
46
53
|
}
|
|
47
54
|
|
|
48
55
|
if (!androidHome) {
|
|
49
|
-
logError('
|
|
56
|
+
logError('Android build-tools not found');
|
|
50
57
|
return null;
|
|
51
58
|
}
|
|
52
59
|
|
package/src/build/gradle.ts
CHANGED
|
@@ -7,7 +7,7 @@ import { spawn, ChildProcess, execSync } from 'child_process';
|
|
|
7
7
|
import * as fs from 'fs';
|
|
8
8
|
import * as path from 'path';
|
|
9
9
|
import * as os from 'os';
|
|
10
|
-
import { BuildConfig, BuildResult } from '@jetstart/shared';
|
|
10
|
+
import { BuildConfig, BuildResult, ErrorSeverity } from '@jetstart/shared';
|
|
11
11
|
import { BuildOutputParser } from './parser';
|
|
12
12
|
|
|
13
13
|
/**
|
|
@@ -289,18 +289,18 @@ export class GradleExecutor {
|
|
|
289
289
|
const startTime = Date.now();
|
|
290
290
|
const gradlePath = this.findGradle(config.projectPath);
|
|
291
291
|
|
|
292
|
-
// If Gradle not found,
|
|
292
|
+
// If Gradle not found, fail build with clear error
|
|
293
293
|
if (!gradlePath) {
|
|
294
|
-
console.log('[Gradle] No Gradle found, returning mock successful build for testing');
|
|
295
|
-
|
|
296
|
-
// Simulate build delay
|
|
297
|
-
await new Promise(resolve => setTimeout(resolve, 2000));
|
|
298
|
-
|
|
299
294
|
return {
|
|
300
|
-
success:
|
|
295
|
+
success: false,
|
|
301
296
|
buildTime: Date.now() - startTime,
|
|
302
|
-
|
|
303
|
-
|
|
297
|
+
errors: [{
|
|
298
|
+
file: 'gradle',
|
|
299
|
+
line: 0,
|
|
300
|
+
column: 0,
|
|
301
|
+
message: 'Gradle not found. Please install Gradle 8.0+ or ensure the Gradle wrapper (gradlew) exists in your project project.',
|
|
302
|
+
severity: ErrorSeverity.ERROR
|
|
303
|
+
}]
|
|
304
304
|
};
|
|
305
305
|
}
|
|
306
306
|
|
|
@@ -82,28 +82,113 @@ export class KotlinCompiler {
|
|
|
82
82
|
|
|
83
83
|
/**
|
|
84
84
|
* Find kotlinc executable
|
|
85
|
+
*
|
|
86
|
+
* Search order:
|
|
87
|
+
* 1. KOTLIN_HOME env var (set in .env or shell)
|
|
88
|
+
* 2. ANDROID_STUDIO_HOME env var
|
|
89
|
+
* 3. Platform-specific static paths (Scoop, Chocolatey, SDKMAN, snap, …)
|
|
90
|
+
* 4. Versioned IDE directories (IntelliJ IDEA, JetBrains Toolbox, Android Studio)
|
|
91
|
+
* 5. `where` / `which` fallback
|
|
85
92
|
*/
|
|
86
93
|
async findKotlinc(): Promise<string | null> {
|
|
87
94
|
if (this.kotlincPath) return this.kotlincPath;
|
|
88
95
|
|
|
89
|
-
|
|
90
|
-
const
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
96
|
+
const win = os.platform() === 'win32';
|
|
97
|
+
const localAppData = process.env.LOCALAPPDATA || path.join(os.homedir(), 'AppData', 'Local');
|
|
98
|
+
const progFiles = process.env.PROGRAMFILES || 'C:\\Program Files';
|
|
99
|
+
|
|
100
|
+
/**
|
|
101
|
+
* Scan `parentDir` for subdirectories whose names start with `entryPrefix`
|
|
102
|
+
* (pass '' to accept any entry), then return the first candidate that exists:
|
|
103
|
+
* path.join(parentDir, entry, ...rest)
|
|
104
|
+
* Entries are sorted descending so the latest version is tried first.
|
|
105
|
+
* Returns null (never throws) if the directory is missing or unreadable.
|
|
106
|
+
*/
|
|
107
|
+
const findInVersionedDir = (
|
|
108
|
+
parentDir: string,
|
|
109
|
+
entryPrefix: string,
|
|
110
|
+
...rest: string[]
|
|
111
|
+
): string | null => {
|
|
112
|
+
try {
|
|
113
|
+
if (!fs.existsSync(parentDir)) return null;
|
|
114
|
+
const entries = fs.readdirSync(parentDir)
|
|
115
|
+
.filter(e => !entryPrefix || e.toLowerCase().startsWith(entryPrefix.toLowerCase()))
|
|
116
|
+
.sort()
|
|
117
|
+
.reverse(); // latest version first
|
|
118
|
+
for (const entry of entries) {
|
|
119
|
+
const candidate = path.join(parentDir, entry, ...rest);
|
|
120
|
+
if (fs.existsSync(candidate)) return candidate;
|
|
121
|
+
}
|
|
122
|
+
} catch { /* permission / access errors — silently skip */ }
|
|
123
|
+
return null;
|
|
124
|
+
};
|
|
125
|
+
|
|
126
|
+
const homeDir = os.homedir();
|
|
127
|
+
// JetStart installs kotlinc here when the user runs --full-install
|
|
128
|
+
const jetstartKotlinc = win
|
|
129
|
+
? path.join(homeDir, '.jetstart', 'kotlinc', 'bin', 'kotlinc.bat')
|
|
130
|
+
: path.join(homeDir, '.jetstart', 'kotlinc', 'bin', 'kotlinc');
|
|
131
|
+
|
|
132
|
+
// Validate KOTLIN_HOME if set — only use it when it actually points to kotlinc
|
|
133
|
+
const kotlinHomeCandidate = process.env.KOTLIN_HOME
|
|
134
|
+
? (win
|
|
135
|
+
? path.join(process.env.KOTLIN_HOME, 'bin', 'kotlinc.bat')
|
|
136
|
+
: path.join(process.env.KOTLIN_HOME, 'bin', 'kotlinc'))
|
|
137
|
+
: null;
|
|
138
|
+
|
|
139
|
+
const locations: Array<string | null> = [
|
|
140
|
+
// JetStart managed install (~/.jetstart/kotlinc) — checked first
|
|
141
|
+
jetstartKotlinc,
|
|
142
|
+
|
|
143
|
+
// env overrides (validated)
|
|
144
|
+
kotlinHomeCandidate,
|
|
145
|
+
process.env.ANDROID_STUDIO_HOME
|
|
146
|
+
? path.join(process.env.ANDROID_STUDIO_HOME, 'plugins', 'Kotlin', 'kotlinc', 'bin', 'kotlinc')
|
|
147
|
+
: null,
|
|
148
|
+
|
|
149
|
+
// Windows static paths
|
|
150
|
+
win ? path.join(progFiles, 'kotlinc', 'bin', 'kotlinc.bat') : null,
|
|
151
|
+
win ? 'C:\\kotlinc\\bin\\kotlinc.bat' : null,
|
|
152
|
+
// Scoop (~\scoop\apps\kotlin\current)
|
|
153
|
+
win ? path.join(homeDir, 'scoop', 'apps', 'kotlin', 'current', 'bin', 'kotlinc.bat') : null,
|
|
154
|
+
// Chocolatey
|
|
155
|
+
win ? 'C:\\ProgramData\\chocolatey\\bin\\kotlinc.bat' : null,
|
|
156
|
+
// Android Studio — standard Google installer
|
|
157
|
+
win ? path.join(progFiles, 'Android', 'Android Studio', 'plugins', 'Kotlin', 'kotlinc', 'bin', 'kotlinc.bat') : null,
|
|
158
|
+
win ? path.join(localAppData,'Programs', 'Android Studio', 'plugins', 'Kotlin', 'kotlinc', 'bin', 'kotlinc.bat') : null,
|
|
159
|
+
|
|
160
|
+
// Windows versioned IDE paths (wildcard scan)
|
|
161
|
+
// IntelliJ IDEA — any version under C:\Program Files\JetBrains
|
|
162
|
+
win ? findInVersionedDir(path.join(progFiles, 'JetBrains'), 'IntelliJ IDEA',
|
|
163
|
+
'plugins', 'Kotlin', 'kotlinc', 'bin', 'kotlinc.bat') : null,
|
|
164
|
+
// JetBrains Toolbox — IDEA Ultimate
|
|
165
|
+
win ? findInVersionedDir(path.join(localAppData, 'JetBrains', 'Toolbox', 'apps', 'IDEA-U', 'ch-0'), '',
|
|
166
|
+
'plugins', 'Kotlin', 'kotlinc', 'bin', 'kotlinc.bat') : null,
|
|
167
|
+
// JetBrains Toolbox — IDEA Community
|
|
168
|
+
win ? findInVersionedDir(path.join(localAppData, 'JetBrains', 'Toolbox', 'apps', 'IDEA-C', 'ch-0'), '',
|
|
169
|
+
'plugins', 'Kotlin', 'kotlinc', 'bin', 'kotlinc.bat') : null,
|
|
170
|
+
// JetBrains Toolbox — Android Studio (Jellyfish+)
|
|
171
|
+
win ? findInVersionedDir(path.join(localAppData, 'JetBrains', 'Toolbox', 'apps', 'AndroidStudio', 'ch-0'), '',
|
|
172
|
+
'plugins', 'Kotlin', 'kotlinc', 'bin', 'kotlinc.bat') : null,
|
|
173
|
+
|
|
174
|
+
// Unix / macOS static paths
|
|
175
|
+
!win ? '/usr/local/bin/kotlinc' : null,
|
|
176
|
+
!win ? '/usr/bin/kotlinc' : null,
|
|
177
|
+
// Homebrew (Apple Silicon + Intel)
|
|
178
|
+
!win ? '/opt/homebrew/bin/kotlinc' : null,
|
|
179
|
+
!win ? '/usr/local/opt/kotlin/bin/kotlinc' : null,
|
|
180
|
+
// SDKMAN (~/.sdkman/candidates/kotlin/current)
|
|
181
|
+
!win ? path.join(homeDir, '.sdkman', 'candidates', 'kotlin', 'current', 'bin', 'kotlinc') : null,
|
|
182
|
+
// Snap
|
|
183
|
+
!win ? '/snap/bin/kotlinc' : null,
|
|
184
|
+
// IntelliJ IDEA — Linux Toolbox
|
|
185
|
+
!win ? findInVersionedDir(path.join(homeDir, '.local', 'share', 'JetBrains', 'Toolbox', 'apps', 'IDEA-U', 'ch-0'), '',
|
|
186
|
+
'plugins', 'Kotlin', 'kotlinc', 'bin', 'kotlinc') : null,
|
|
187
|
+
];
|
|
104
188
|
|
|
105
189
|
for (const loc of locations) {
|
|
106
|
-
|
|
190
|
+
if (!loc) continue;
|
|
191
|
+
const execPath = win && !loc.endsWith('.bat') ? `${loc}.bat` : loc;
|
|
107
192
|
if (fs.existsSync(execPath)) {
|
|
108
193
|
this.kotlincPath = execPath;
|
|
109
194
|
log(`Found kotlinc at: ${execPath}`);
|
|
@@ -113,7 +198,7 @@ export class KotlinCompiler {
|
|
|
113
198
|
|
|
114
199
|
// Try to find via 'where' (Windows) or 'which' (Unix)
|
|
115
200
|
try {
|
|
116
|
-
const cmd =
|
|
201
|
+
const cmd = win ? 'where' : 'which';
|
|
117
202
|
const result = await this.runCommand(cmd, ['kotlinc']);
|
|
118
203
|
if (result.success && result.stdout.trim()) {
|
|
119
204
|
this.kotlincPath = result.stdout.trim().split('\n')[0];
|