uloop-cli 0.56.0 → 0.58.0
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/cli.bundle.cjs +729 -17
- package/dist/cli.bundle.cjs.map +4 -4
- package/package.json +7 -6
- package/src/__tests__/cli-e2e.test.ts +40 -0
- package/src/cli.ts +22 -1
- package/src/commands/focus-window.ts +59 -0
- package/src/commands/launch.ts +125 -0
- package/src/default-tools.json +1 -1
- package/src/direct-unity-client.ts +1 -1
- package/src/skills/skill-definitions/cli-only/uloop-focus-window/SKILL.md +36 -0
- package/src/skills/skill-definitions/cli-only/uloop-launch/Skill/SKILL.md +51 -0
- package/src/version.ts +1 -1
package/dist/cli.bundle.cjs
CHANGED
|
@@ -5384,7 +5384,7 @@ var require_semver2 = __commonJS({
|
|
|
5384
5384
|
|
|
5385
5385
|
// src/cli.ts
|
|
5386
5386
|
var import_fs6 = require("fs");
|
|
5387
|
-
var
|
|
5387
|
+
var import_path7 = require("path");
|
|
5388
5388
|
var import_os2 = require("os");
|
|
5389
5389
|
var import_child_process = require("child_process");
|
|
5390
5390
|
|
|
@@ -5486,13 +5486,13 @@ var DirectUnityClient = class {
|
|
|
5486
5486
|
requestId = 0;
|
|
5487
5487
|
receiveBuffer = Buffer.alloc(0);
|
|
5488
5488
|
async connect() {
|
|
5489
|
-
return new Promise((
|
|
5489
|
+
return new Promise((resolve5, reject) => {
|
|
5490
5490
|
this.socket = new net.Socket();
|
|
5491
5491
|
this.socket.on("error", (error) => {
|
|
5492
5492
|
reject(new Error(`Connection error: ${error.message}`));
|
|
5493
5493
|
});
|
|
5494
5494
|
this.socket.connect(this.port, this.host, () => {
|
|
5495
|
-
|
|
5495
|
+
resolve5();
|
|
5496
5496
|
});
|
|
5497
5497
|
});
|
|
5498
5498
|
}
|
|
@@ -5508,12 +5508,12 @@ var DirectUnityClient = class {
|
|
|
5508
5508
|
};
|
|
5509
5509
|
const requestJson = JSON.stringify(request);
|
|
5510
5510
|
const framedMessage = createFrame(requestJson);
|
|
5511
|
-
return new Promise((
|
|
5511
|
+
return new Promise((resolve5, reject) => {
|
|
5512
5512
|
const socket = this.socket;
|
|
5513
5513
|
const timeoutId = setTimeout(() => {
|
|
5514
5514
|
reject(
|
|
5515
5515
|
new Error(
|
|
5516
|
-
`Request timed out after ${NETWORK_TIMEOUT_MS}ms. Unity may be frozen or busy. [For AI]
|
|
5516
|
+
`Request timed out after ${NETWORK_TIMEOUT_MS}ms. Unity may be frozen or busy. [For AI] Run 'uloop focus-window' to bring Unity to the front, then retry the tool. If the issue persists, report this to the user and ask how to proceed. Do NOT kill Unity processes without user permission.`
|
|
5517
5517
|
)
|
|
5518
5518
|
);
|
|
5519
5519
|
}, NETWORK_TIMEOUT_MS);
|
|
@@ -5539,7 +5539,7 @@ var DirectUnityClient = class {
|
|
|
5539
5539
|
reject(new Error(`Unity error: ${response.error.message}`));
|
|
5540
5540
|
return;
|
|
5541
5541
|
}
|
|
5542
|
-
|
|
5542
|
+
resolve5(response.result);
|
|
5543
5543
|
};
|
|
5544
5544
|
socket.on("data", onData);
|
|
5545
5545
|
socket.write(framedMessage);
|
|
@@ -5763,7 +5763,7 @@ var import_path3 = require("path");
|
|
|
5763
5763
|
|
|
5764
5764
|
// src/default-tools.json
|
|
5765
5765
|
var default_tools_default = {
|
|
5766
|
-
version: "0.
|
|
5766
|
+
version: "0.58.0",
|
|
5767
5767
|
tools: [
|
|
5768
5768
|
{
|
|
5769
5769
|
name: "compile",
|
|
@@ -6215,7 +6215,7 @@ function getCachedServerVersion() {
|
|
|
6215
6215
|
}
|
|
6216
6216
|
|
|
6217
6217
|
// src/version.ts
|
|
6218
|
-
var VERSION = "0.
|
|
6218
|
+
var VERSION = "0.58.0";
|
|
6219
6219
|
|
|
6220
6220
|
// src/spinner.ts
|
|
6221
6221
|
var SPINNER_FRAMES = ["\u280B", "\u2819", "\u2839", "\u2838", "\u283C", "\u2834", "\u2826", "\u2827", "\u2807", "\u280F"];
|
|
@@ -6278,7 +6278,7 @@ function suppressStdinEcho() {
|
|
|
6278
6278
|
var RETRY_DELAY_MS = 500;
|
|
6279
6279
|
var MAX_RETRIES = 3;
|
|
6280
6280
|
function sleep(ms) {
|
|
6281
|
-
return new Promise((
|
|
6281
|
+
return new Promise((resolve5) => setTimeout(resolve5, ms));
|
|
6282
6282
|
}
|
|
6283
6283
|
function isRetryableError(error) {
|
|
6284
6284
|
if (!(error instanceof Error)) {
|
|
@@ -7250,8 +7250,715 @@ Uninstalling uloop skills (${location})...`);
|
|
|
7250
7250
|
}
|
|
7251
7251
|
}
|
|
7252
7252
|
|
|
7253
|
+
// src/commands/launch.ts
|
|
7254
|
+
var import_path6 = require("path");
|
|
7255
|
+
|
|
7256
|
+
// node_modules/launch-unity/dist/lib.js
|
|
7257
|
+
var import_node_child_process = require("node:child_process");
|
|
7258
|
+
var import_node_fs2 = require("node:fs");
|
|
7259
|
+
var import_promises3 = require("node:fs/promises");
|
|
7260
|
+
var import_node_path2 = require("node:path");
|
|
7261
|
+
var import_node_util = require("node:util");
|
|
7262
|
+
|
|
7263
|
+
// node_modules/launch-unity/dist/unityHub.js
|
|
7264
|
+
var import_promises2 = require("node:fs/promises");
|
|
7265
|
+
var import_node_fs = require("node:fs");
|
|
7266
|
+
var import_node_path = require("node:path");
|
|
7267
|
+
var resolveUnityHubProjectFiles = () => {
|
|
7268
|
+
if (process.platform === "darwin") {
|
|
7269
|
+
const home = process.env.HOME;
|
|
7270
|
+
if (!home) {
|
|
7271
|
+
return [];
|
|
7272
|
+
}
|
|
7273
|
+
const base = (0, import_node_path.join)(home, "Library", "Application Support", "UnityHub");
|
|
7274
|
+
return [(0, import_node_path.join)(base, "projects-v1.json"), (0, import_node_path.join)(base, "projects.json")];
|
|
7275
|
+
}
|
|
7276
|
+
if (process.platform === "win32") {
|
|
7277
|
+
const appData = process.env.APPDATA;
|
|
7278
|
+
if (!appData) {
|
|
7279
|
+
return [];
|
|
7280
|
+
}
|
|
7281
|
+
const base = (0, import_node_path.join)(appData, "UnityHub");
|
|
7282
|
+
return [(0, import_node_path.join)(base, "projects-v1.json"), (0, import_node_path.join)(base, "projects.json")];
|
|
7283
|
+
}
|
|
7284
|
+
return [];
|
|
7285
|
+
};
|
|
7286
|
+
var removeTrailingSeparators = (target) => {
|
|
7287
|
+
let trimmed = target;
|
|
7288
|
+
while (trimmed.length > 1 && (trimmed.endsWith("/") || trimmed.endsWith("\\"))) {
|
|
7289
|
+
trimmed = trimmed.slice(0, -1);
|
|
7290
|
+
}
|
|
7291
|
+
return trimmed;
|
|
7292
|
+
};
|
|
7293
|
+
var normalizePath = (target) => {
|
|
7294
|
+
const resolvedPath = (0, import_node_path.resolve)(target);
|
|
7295
|
+
return removeTrailingSeparators(resolvedPath);
|
|
7296
|
+
};
|
|
7297
|
+
var resolvePathWithActualCase = (target) => {
|
|
7298
|
+
try {
|
|
7299
|
+
return removeTrailingSeparators(import_node_fs.realpathSync.native(target));
|
|
7300
|
+
} catch {
|
|
7301
|
+
return normalizePath(target);
|
|
7302
|
+
}
|
|
7303
|
+
};
|
|
7304
|
+
var toComparablePath = (value) => {
|
|
7305
|
+
return value.replace(/\\/g, "/").toLocaleLowerCase();
|
|
7306
|
+
};
|
|
7307
|
+
var pathsEqual = (left, right) => {
|
|
7308
|
+
return toComparablePath(normalizePath(left)) === toComparablePath(normalizePath(right));
|
|
7309
|
+
};
|
|
7310
|
+
var safeParseProjectsJson = (content) => {
|
|
7311
|
+
try {
|
|
7312
|
+
return JSON.parse(content);
|
|
7313
|
+
} catch {
|
|
7314
|
+
return void 0;
|
|
7315
|
+
}
|
|
7316
|
+
};
|
|
7317
|
+
var logDebug = (message) => {
|
|
7318
|
+
if (process.env["LAUNCH_UNITY_DEBUG"] === "1") {
|
|
7319
|
+
console.log(`[unityHub] ${message}`);
|
|
7320
|
+
}
|
|
7321
|
+
};
|
|
7322
|
+
var ensureProjectEntryAndUpdate = async (projectPath, version, when, setFavorite = false) => {
|
|
7323
|
+
const canonicalProjectPath = resolvePathWithActualCase(projectPath);
|
|
7324
|
+
const projectTitle = (0, import_node_path.basename)(canonicalProjectPath);
|
|
7325
|
+
const containingFolderPath = (0, import_node_path.dirname)(canonicalProjectPath);
|
|
7326
|
+
const candidates = resolveUnityHubProjectFiles();
|
|
7327
|
+
if (candidates.length === 0) {
|
|
7328
|
+
logDebug("No Unity Hub project files found.");
|
|
7329
|
+
return;
|
|
7330
|
+
}
|
|
7331
|
+
for (const path of candidates) {
|
|
7332
|
+
logDebug(`Trying Unity Hub file: ${path}`);
|
|
7333
|
+
const content = await (0, import_promises2.readFile)(path, "utf8").catch(() => void 0);
|
|
7334
|
+
if (!content) {
|
|
7335
|
+
logDebug("Read failed or empty content, skipping.");
|
|
7336
|
+
continue;
|
|
7337
|
+
}
|
|
7338
|
+
const json = safeParseProjectsJson(content);
|
|
7339
|
+
if (!json) {
|
|
7340
|
+
logDebug("Parse failed, skipping.");
|
|
7341
|
+
continue;
|
|
7342
|
+
}
|
|
7343
|
+
const data = { ...json.data ?? {} };
|
|
7344
|
+
const existingKey = Object.keys(data).find((key) => {
|
|
7345
|
+
const entryPath = data[key]?.path;
|
|
7346
|
+
return entryPath ? pathsEqual(entryPath, projectPath) : false;
|
|
7347
|
+
});
|
|
7348
|
+
const targetKey = existingKey ?? canonicalProjectPath;
|
|
7349
|
+
const existingEntry = existingKey ? data[existingKey] : void 0;
|
|
7350
|
+
logDebug(existingKey ? `Found existing entry for project (key=${existingKey}). Updating lastModified.` : `No existing entry. Adding new entry (key=${targetKey}).`);
|
|
7351
|
+
const updatedEntry = {
|
|
7352
|
+
...existingEntry,
|
|
7353
|
+
path: existingEntry?.path ?? canonicalProjectPath,
|
|
7354
|
+
containingFolderPath: existingEntry?.containingFolderPath ?? containingFolderPath,
|
|
7355
|
+
version: existingEntry?.version ?? version,
|
|
7356
|
+
title: existingEntry?.title ?? projectTitle,
|
|
7357
|
+
lastModified: when.getTime(),
|
|
7358
|
+
isFavorite: setFavorite ? true : existingEntry?.isFavorite ?? false
|
|
7359
|
+
};
|
|
7360
|
+
const updatedJson = {
|
|
7361
|
+
...json,
|
|
7362
|
+
data: {
|
|
7363
|
+
...data,
|
|
7364
|
+
[targetKey]: updatedEntry
|
|
7365
|
+
}
|
|
7366
|
+
};
|
|
7367
|
+
try {
|
|
7368
|
+
await (0, import_promises2.writeFile)(path, JSON.stringify(updatedJson, void 0, 2), "utf8");
|
|
7369
|
+
logDebug("Write succeeded.");
|
|
7370
|
+
} catch (error) {
|
|
7371
|
+
logDebug(`Write failed: ${error instanceof Error ? error.message : String(error)}`);
|
|
7372
|
+
}
|
|
7373
|
+
return;
|
|
7374
|
+
}
|
|
7375
|
+
};
|
|
7376
|
+
var updateLastModifiedIfExists = async (projectPath, when) => {
|
|
7377
|
+
const candidates = resolveUnityHubProjectFiles();
|
|
7378
|
+
if (candidates.length === 0) {
|
|
7379
|
+
return;
|
|
7380
|
+
}
|
|
7381
|
+
for (const path of candidates) {
|
|
7382
|
+
let content;
|
|
7383
|
+
let json;
|
|
7384
|
+
try {
|
|
7385
|
+
content = await (0, import_promises2.readFile)(path, "utf8");
|
|
7386
|
+
} catch {
|
|
7387
|
+
continue;
|
|
7388
|
+
}
|
|
7389
|
+
try {
|
|
7390
|
+
json = JSON.parse(content);
|
|
7391
|
+
} catch {
|
|
7392
|
+
continue;
|
|
7393
|
+
}
|
|
7394
|
+
if (!json.data) {
|
|
7395
|
+
return;
|
|
7396
|
+
}
|
|
7397
|
+
const projectKey = Object.keys(json.data).find((key) => {
|
|
7398
|
+
const entryPath = json.data?.[key]?.path;
|
|
7399
|
+
return entryPath ? pathsEqual(entryPath, projectPath) : false;
|
|
7400
|
+
});
|
|
7401
|
+
if (!projectKey) {
|
|
7402
|
+
return;
|
|
7403
|
+
}
|
|
7404
|
+
const original = json.data[projectKey];
|
|
7405
|
+
if (!original) {
|
|
7406
|
+
return;
|
|
7407
|
+
}
|
|
7408
|
+
json.data[projectKey] = {
|
|
7409
|
+
...original,
|
|
7410
|
+
lastModified: when.getTime()
|
|
7411
|
+
};
|
|
7412
|
+
try {
|
|
7413
|
+
await (0, import_promises2.writeFile)(path, JSON.stringify(json, void 0, 2), "utf8");
|
|
7414
|
+
} catch {
|
|
7415
|
+
}
|
|
7416
|
+
return;
|
|
7417
|
+
}
|
|
7418
|
+
};
|
|
7419
|
+
|
|
7420
|
+
// node_modules/launch-unity/dist/lib.js
|
|
7421
|
+
var execFileAsync = (0, import_node_util.promisify)(import_node_child_process.execFile);
|
|
7422
|
+
var UNITY_EXECUTABLE_PATTERN_MAC = /Unity\.app\/Contents\/MacOS\/Unity/i;
|
|
7423
|
+
var UNITY_EXECUTABLE_PATTERN_WINDOWS = /Unity\.exe/i;
|
|
7424
|
+
var PROJECT_PATH_PATTERN = /-(?:projectPath|projectpath)(?:=|\s+)("[^"]+"|'[^']+'|[^\s"']+)/i;
|
|
7425
|
+
var PROCESS_LIST_COMMAND_MAC = "ps";
|
|
7426
|
+
var PROCESS_LIST_ARGS_MAC = ["-axo", "pid=,command=", "-ww"];
|
|
7427
|
+
var WINDOWS_POWERSHELL = "powershell";
|
|
7428
|
+
var UNITY_LOCKFILE_NAME = "UnityLockfile";
|
|
7429
|
+
var TEMP_DIRECTORY_NAME = "Temp";
|
|
7430
|
+
function getUnityVersion(projectPath) {
|
|
7431
|
+
const versionFile = (0, import_node_path2.join)(projectPath, "ProjectSettings", "ProjectVersion.txt");
|
|
7432
|
+
if (!(0, import_node_fs2.existsSync)(versionFile)) {
|
|
7433
|
+
throw new Error(`ProjectVersion.txt not found at ${versionFile}. This does not appear to be a Unity project.`);
|
|
7434
|
+
}
|
|
7435
|
+
const content = (0, import_node_fs2.readFileSync)(versionFile, "utf8");
|
|
7436
|
+
const version = content.match(/m_EditorVersion:\s*([^\s\n]+)/)?.[1];
|
|
7437
|
+
if (!version) {
|
|
7438
|
+
throw new Error(`Could not extract Unity version from ${versionFile}`);
|
|
7439
|
+
}
|
|
7440
|
+
return version;
|
|
7441
|
+
}
|
|
7442
|
+
function getUnityPathWindows(version) {
|
|
7443
|
+
const candidates = [];
|
|
7444
|
+
const programFiles = process.env["PROGRAMFILES"];
|
|
7445
|
+
const programFilesX86 = process.env["PROGRAMFILES(X86)"];
|
|
7446
|
+
const localAppData = process.env["LOCALAPPDATA"];
|
|
7447
|
+
const addCandidate = (base) => {
|
|
7448
|
+
if (!base) {
|
|
7449
|
+
return;
|
|
7450
|
+
}
|
|
7451
|
+
candidates.push((0, import_node_path2.join)(base, "Unity", "Hub", "Editor", version, "Editor", "Unity.exe"));
|
|
7452
|
+
};
|
|
7453
|
+
addCandidate(programFiles);
|
|
7454
|
+
addCandidate(programFilesX86);
|
|
7455
|
+
addCandidate(localAppData);
|
|
7456
|
+
candidates.push((0, import_node_path2.join)("C:\\", "Program Files", "Unity", "Hub", "Editor", version, "Editor", "Unity.exe"));
|
|
7457
|
+
for (const candidate of candidates) {
|
|
7458
|
+
if ((0, import_node_fs2.existsSync)(candidate)) {
|
|
7459
|
+
return candidate;
|
|
7460
|
+
}
|
|
7461
|
+
}
|
|
7462
|
+
return candidates[0] ?? (0, import_node_path2.join)("C:\\", "Program Files", "Unity", "Hub", "Editor", version, "Editor", "Unity.exe");
|
|
7463
|
+
}
|
|
7464
|
+
function getUnityPath(version) {
|
|
7465
|
+
if (process.platform === "darwin") {
|
|
7466
|
+
return `/Applications/Unity/Hub/Editor/${version}/Unity.app/Contents/MacOS/Unity`;
|
|
7467
|
+
}
|
|
7468
|
+
if (process.platform === "win32") {
|
|
7469
|
+
return getUnityPathWindows(version);
|
|
7470
|
+
}
|
|
7471
|
+
return `/Applications/Unity/Hub/Editor/${version}/Unity.app/Contents/MacOS/Unity`;
|
|
7472
|
+
}
|
|
7473
|
+
var removeTrailingSeparators2 = (target) => {
|
|
7474
|
+
let trimmed = target;
|
|
7475
|
+
while (trimmed.length > 1 && (trimmed.endsWith("/") || trimmed.endsWith("\\"))) {
|
|
7476
|
+
trimmed = trimmed.slice(0, -1);
|
|
7477
|
+
}
|
|
7478
|
+
return trimmed;
|
|
7479
|
+
};
|
|
7480
|
+
var normalizePath2 = (target) => {
|
|
7481
|
+
const resolvedPath = (0, import_node_path2.resolve)(target);
|
|
7482
|
+
const trimmed = removeTrailingSeparators2(resolvedPath);
|
|
7483
|
+
return trimmed;
|
|
7484
|
+
};
|
|
7485
|
+
var toComparablePath2 = (value) => {
|
|
7486
|
+
return value.replace(/\\/g, "/").toLocaleLowerCase();
|
|
7487
|
+
};
|
|
7488
|
+
var pathsEqual2 = (left, right) => {
|
|
7489
|
+
return toComparablePath2(normalizePath2(left)) === toComparablePath2(normalizePath2(right));
|
|
7490
|
+
};
|
|
7491
|
+
function extractProjectPath(command) {
|
|
7492
|
+
const match = command.match(PROJECT_PATH_PATTERN);
|
|
7493
|
+
if (!match) {
|
|
7494
|
+
return void 0;
|
|
7495
|
+
}
|
|
7496
|
+
const raw = match[1];
|
|
7497
|
+
if (!raw) {
|
|
7498
|
+
return void 0;
|
|
7499
|
+
}
|
|
7500
|
+
const trimmed = raw.trim();
|
|
7501
|
+
if (trimmed.startsWith('"') && trimmed.endsWith('"')) {
|
|
7502
|
+
return trimmed.slice(1, -1);
|
|
7503
|
+
}
|
|
7504
|
+
if (trimmed.startsWith("'") && trimmed.endsWith("'")) {
|
|
7505
|
+
return trimmed.slice(1, -1);
|
|
7506
|
+
}
|
|
7507
|
+
return trimmed;
|
|
7508
|
+
}
|
|
7509
|
+
var isUnityAuxiliaryProcess = (command) => {
|
|
7510
|
+
const normalizedCommand = command.toLowerCase();
|
|
7511
|
+
if (normalizedCommand.includes("-batchmode")) {
|
|
7512
|
+
return true;
|
|
7513
|
+
}
|
|
7514
|
+
return normalizedCommand.includes("assetimportworker");
|
|
7515
|
+
};
|
|
7516
|
+
async function listUnityProcessesMac() {
|
|
7517
|
+
let stdout = "";
|
|
7518
|
+
try {
|
|
7519
|
+
const result = await execFileAsync(PROCESS_LIST_COMMAND_MAC, PROCESS_LIST_ARGS_MAC);
|
|
7520
|
+
stdout = result.stdout;
|
|
7521
|
+
} catch (error) {
|
|
7522
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
7523
|
+
console.error(`Failed to retrieve Unity process list: ${message}`);
|
|
7524
|
+
return [];
|
|
7525
|
+
}
|
|
7526
|
+
const lines = stdout.split("\n").map((line) => line.trim()).filter((line) => line.length > 0);
|
|
7527
|
+
const processes = [];
|
|
7528
|
+
for (const line of lines) {
|
|
7529
|
+
const match = line.match(/^(\d+)\s+(.*)$/);
|
|
7530
|
+
if (!match) {
|
|
7531
|
+
continue;
|
|
7532
|
+
}
|
|
7533
|
+
const pidValue = Number.parseInt(match[1] ?? "", 10);
|
|
7534
|
+
if (!Number.isFinite(pidValue)) {
|
|
7535
|
+
continue;
|
|
7536
|
+
}
|
|
7537
|
+
const command = match[2] ?? "";
|
|
7538
|
+
if (!UNITY_EXECUTABLE_PATTERN_MAC.test(command)) {
|
|
7539
|
+
continue;
|
|
7540
|
+
}
|
|
7541
|
+
if (isUnityAuxiliaryProcess(command)) {
|
|
7542
|
+
continue;
|
|
7543
|
+
}
|
|
7544
|
+
const projectArgument = extractProjectPath(command);
|
|
7545
|
+
if (!projectArgument) {
|
|
7546
|
+
continue;
|
|
7547
|
+
}
|
|
7548
|
+
processes.push({
|
|
7549
|
+
pid: pidValue,
|
|
7550
|
+
projectPath: normalizePath2(projectArgument)
|
|
7551
|
+
});
|
|
7552
|
+
}
|
|
7553
|
+
return processes;
|
|
7554
|
+
}
|
|
7555
|
+
async function listUnityProcessesWindows() {
|
|
7556
|
+
const scriptLines = [
|
|
7557
|
+
"$ErrorActionPreference = 'Stop'",
|
|
7558
|
+
`$processes = Get-CimInstance Win32_Process -Filter "Name = 'Unity.exe'" | Where-Object { $_.CommandLine }`,
|
|
7559
|
+
"foreach ($process in $processes) {",
|
|
7560
|
+
` $commandLine = $process.CommandLine -replace "\`r", ' ' -replace "\`n", ' '`,
|
|
7561
|
+
' Write-Output ("{0}|{1}" -f $process.ProcessId, $commandLine)',
|
|
7562
|
+
"}"
|
|
7563
|
+
];
|
|
7564
|
+
let stdout = "";
|
|
7565
|
+
try {
|
|
7566
|
+
const result = await execFileAsync(WINDOWS_POWERSHELL, ["-NoProfile", "-Command", scriptLines.join("\n")]);
|
|
7567
|
+
stdout = result.stdout ?? "";
|
|
7568
|
+
} catch (error) {
|
|
7569
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
7570
|
+
console.error(`Failed to retrieve Unity process list on Windows: ${message}`);
|
|
7571
|
+
return [];
|
|
7572
|
+
}
|
|
7573
|
+
const lines = stdout.split("\n").map((line) => line.trim()).filter((line) => line.length > 0);
|
|
7574
|
+
const processes = [];
|
|
7575
|
+
for (const line of lines) {
|
|
7576
|
+
const delimiterIndex = line.indexOf("|");
|
|
7577
|
+
if (delimiterIndex < 0) {
|
|
7578
|
+
continue;
|
|
7579
|
+
}
|
|
7580
|
+
const pidText = line.slice(0, delimiterIndex).trim();
|
|
7581
|
+
const command = line.slice(delimiterIndex + 1).trim();
|
|
7582
|
+
const pidValue = Number.parseInt(pidText, 10);
|
|
7583
|
+
if (!Number.isFinite(pidValue)) {
|
|
7584
|
+
continue;
|
|
7585
|
+
}
|
|
7586
|
+
if (!UNITY_EXECUTABLE_PATTERN_WINDOWS.test(command)) {
|
|
7587
|
+
continue;
|
|
7588
|
+
}
|
|
7589
|
+
if (isUnityAuxiliaryProcess(command)) {
|
|
7590
|
+
continue;
|
|
7591
|
+
}
|
|
7592
|
+
const projectArgument = extractProjectPath(command);
|
|
7593
|
+
if (!projectArgument) {
|
|
7594
|
+
continue;
|
|
7595
|
+
}
|
|
7596
|
+
processes.push({
|
|
7597
|
+
pid: pidValue,
|
|
7598
|
+
projectPath: normalizePath2(projectArgument)
|
|
7599
|
+
});
|
|
7600
|
+
}
|
|
7601
|
+
return processes;
|
|
7602
|
+
}
|
|
7603
|
+
async function listUnityProcesses() {
|
|
7604
|
+
if (process.platform === "darwin") {
|
|
7605
|
+
return await listUnityProcessesMac();
|
|
7606
|
+
}
|
|
7607
|
+
if (process.platform === "win32") {
|
|
7608
|
+
return await listUnityProcessesWindows();
|
|
7609
|
+
}
|
|
7610
|
+
return [];
|
|
7611
|
+
}
|
|
7612
|
+
async function findRunningUnityProcess(projectPath) {
|
|
7613
|
+
const normalizedTarget = normalizePath2(projectPath);
|
|
7614
|
+
const processes = await listUnityProcesses();
|
|
7615
|
+
return processes.find((candidate) => pathsEqual2(candidate.projectPath, normalizedTarget));
|
|
7616
|
+
}
|
|
7617
|
+
async function focusUnityProcess(pid) {
|
|
7618
|
+
if (process.platform === "darwin") {
|
|
7619
|
+
await focusUnityProcessMac(pid);
|
|
7620
|
+
return;
|
|
7621
|
+
}
|
|
7622
|
+
if (process.platform === "win32") {
|
|
7623
|
+
await focusUnityProcessWindows(pid);
|
|
7624
|
+
}
|
|
7625
|
+
}
|
|
7626
|
+
async function focusUnityProcessMac(pid) {
|
|
7627
|
+
const script = `tell application "System Events" to set frontmost of (first process whose unix id is ${pid}) to true`;
|
|
7628
|
+
try {
|
|
7629
|
+
await execFileAsync("osascript", ["-e", script]);
|
|
7630
|
+
console.log("Brought existing Unity to the front.");
|
|
7631
|
+
} catch (error) {
|
|
7632
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
7633
|
+
console.warn(`Failed to bring Unity to front: ${message}`);
|
|
7634
|
+
}
|
|
7635
|
+
}
|
|
7636
|
+
async function focusUnityProcessWindows(pid) {
|
|
7637
|
+
const addTypeLines = [
|
|
7638
|
+
'Add-Type -TypeDefinition @"',
|
|
7639
|
+
"using System;",
|
|
7640
|
+
"using System.Runtime.InteropServices;",
|
|
7641
|
+
"public static class Win32Interop {",
|
|
7642
|
+
' [DllImport("user32.dll")] public static extern bool SetForegroundWindow(IntPtr hWnd);',
|
|
7643
|
+
' [DllImport("user32.dll")] public static extern bool ShowWindowAsync(IntPtr hWnd, int nCmdShow);',
|
|
7644
|
+
"}",
|
|
7645
|
+
'"@'
|
|
7646
|
+
];
|
|
7647
|
+
const scriptLines = [
|
|
7648
|
+
"$ErrorActionPreference = 'Stop'",
|
|
7649
|
+
...addTypeLines,
|
|
7650
|
+
`try { $process = Get-Process -Id ${pid} -ErrorAction Stop } catch { return }`,
|
|
7651
|
+
"$handle = $process.MainWindowHandle",
|
|
7652
|
+
"if ($handle -eq 0) { return }",
|
|
7653
|
+
"[Win32Interop]::ShowWindowAsync($handle, 9) | Out-Null",
|
|
7654
|
+
"[Win32Interop]::SetForegroundWindow($handle) | Out-Null"
|
|
7655
|
+
];
|
|
7656
|
+
try {
|
|
7657
|
+
await execFileAsync(WINDOWS_POWERSHELL, ["-NoProfile", "-Command", scriptLines.join("\n")]);
|
|
7658
|
+
console.log("Brought existing Unity to the front.");
|
|
7659
|
+
} catch (error) {
|
|
7660
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
7661
|
+
console.warn(`Failed to bring Unity to front on Windows: ${message}`);
|
|
7662
|
+
}
|
|
7663
|
+
}
|
|
7664
|
+
async function handleStaleLockfile(projectPath) {
|
|
7665
|
+
const tempDirectoryPath = (0, import_node_path2.join)(projectPath, TEMP_DIRECTORY_NAME);
|
|
7666
|
+
const lockfilePath = (0, import_node_path2.join)(tempDirectoryPath, UNITY_LOCKFILE_NAME);
|
|
7667
|
+
if (!(0, import_node_fs2.existsSync)(lockfilePath)) {
|
|
7668
|
+
return;
|
|
7669
|
+
}
|
|
7670
|
+
console.log(`UnityLockfile found without active Unity process: ${lockfilePath}`);
|
|
7671
|
+
console.log("Assuming previous crash. Cleaning Temp directory and continuing launch.");
|
|
7672
|
+
try {
|
|
7673
|
+
await (0, import_promises3.rm)(tempDirectoryPath, { recursive: true, force: true });
|
|
7674
|
+
console.log("Deleted Temp directory.");
|
|
7675
|
+
} catch (error) {
|
|
7676
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
7677
|
+
console.warn(`Failed to delete Temp directory: ${message}`);
|
|
7678
|
+
}
|
|
7679
|
+
try {
|
|
7680
|
+
await (0, import_promises3.rm)(lockfilePath, { force: true });
|
|
7681
|
+
console.log("Deleted UnityLockfile.");
|
|
7682
|
+
} catch (error) {
|
|
7683
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
7684
|
+
console.warn(`Failed to delete UnityLockfile: ${message}`);
|
|
7685
|
+
}
|
|
7686
|
+
}
|
|
7687
|
+
var KILL_POLL_INTERVAL_MS = 100;
|
|
7688
|
+
var KILL_TIMEOUT_MS = 1e4;
|
|
7689
|
+
function isProcessAlive(pid) {
|
|
7690
|
+
try {
|
|
7691
|
+
process.kill(pid, 0);
|
|
7692
|
+
return true;
|
|
7693
|
+
} catch {
|
|
7694
|
+
return false;
|
|
7695
|
+
}
|
|
7696
|
+
}
|
|
7697
|
+
function killProcess(pid) {
|
|
7698
|
+
try {
|
|
7699
|
+
process.kill(pid, "SIGKILL");
|
|
7700
|
+
} catch {
|
|
7701
|
+
}
|
|
7702
|
+
}
|
|
7703
|
+
async function waitForProcessExit(pid) {
|
|
7704
|
+
const start = Date.now();
|
|
7705
|
+
while (Date.now() - start < KILL_TIMEOUT_MS) {
|
|
7706
|
+
if (!isProcessAlive(pid)) {
|
|
7707
|
+
return true;
|
|
7708
|
+
}
|
|
7709
|
+
await new Promise((resolve5) => setTimeout(resolve5, KILL_POLL_INTERVAL_MS));
|
|
7710
|
+
}
|
|
7711
|
+
return false;
|
|
7712
|
+
}
|
|
7713
|
+
async function killRunningUnity(projectPath) {
|
|
7714
|
+
const processInfo = await findRunningUnityProcess(projectPath);
|
|
7715
|
+
if (!processInfo) {
|
|
7716
|
+
console.log("No running Unity process found for this project.");
|
|
7717
|
+
return;
|
|
7718
|
+
}
|
|
7719
|
+
const pid = processInfo.pid;
|
|
7720
|
+
console.log(`Killing Unity (PID: ${pid})...`);
|
|
7721
|
+
killProcess(pid);
|
|
7722
|
+
const exited = await waitForProcessExit(pid);
|
|
7723
|
+
if (!exited) {
|
|
7724
|
+
throw new Error(`Failed to kill Unity (PID: ${pid}) within ${KILL_TIMEOUT_MS / 1e3}s.`);
|
|
7725
|
+
}
|
|
7726
|
+
console.log("Unity killed.");
|
|
7727
|
+
}
|
|
7728
|
+
function hasBuildTargetArg(unityArgs) {
|
|
7729
|
+
for (const arg of unityArgs) {
|
|
7730
|
+
if (arg === "-buildTarget") {
|
|
7731
|
+
return true;
|
|
7732
|
+
}
|
|
7733
|
+
if (arg.startsWith("-buildTarget=")) {
|
|
7734
|
+
return true;
|
|
7735
|
+
}
|
|
7736
|
+
}
|
|
7737
|
+
return false;
|
|
7738
|
+
}
|
|
7739
|
+
var EXCLUDED_DIR_NAMES = /* @__PURE__ */ new Set([
|
|
7740
|
+
"library",
|
|
7741
|
+
"temp",
|
|
7742
|
+
"logs",
|
|
7743
|
+
"obj",
|
|
7744
|
+
".git",
|
|
7745
|
+
"node_modules",
|
|
7746
|
+
".idea",
|
|
7747
|
+
".vscode",
|
|
7748
|
+
".vs"
|
|
7749
|
+
]);
|
|
7750
|
+
function isUnityProjectRoot(candidateDir) {
|
|
7751
|
+
const versionFile = (0, import_node_path2.join)(candidateDir, "ProjectSettings", "ProjectVersion.txt");
|
|
7752
|
+
return (0, import_node_fs2.existsSync)(versionFile);
|
|
7753
|
+
}
|
|
7754
|
+
function listSubdirectoriesSorted(dir) {
|
|
7755
|
+
let entries = [];
|
|
7756
|
+
try {
|
|
7757
|
+
const dirents = (0, import_node_fs2.readdirSync)(dir, { withFileTypes: true });
|
|
7758
|
+
const subdirs = dirents.filter((d) => d.isDirectory()).map((d) => d.name).filter((name) => !EXCLUDED_DIR_NAMES.has(name.toLocaleLowerCase()));
|
|
7759
|
+
subdirs.sort((a, b) => a.localeCompare(b));
|
|
7760
|
+
entries = subdirs.map((name) => (0, import_node_path2.join)(dir, name));
|
|
7761
|
+
} catch {
|
|
7762
|
+
entries = [];
|
|
7763
|
+
}
|
|
7764
|
+
return entries;
|
|
7765
|
+
}
|
|
7766
|
+
function findUnityProjectBfs(rootDir, maxDepth) {
|
|
7767
|
+
const queue = [];
|
|
7768
|
+
let rootCanonical;
|
|
7769
|
+
try {
|
|
7770
|
+
rootCanonical = (0, import_node_fs2.realpathSync)(rootDir);
|
|
7771
|
+
} catch {
|
|
7772
|
+
rootCanonical = rootDir;
|
|
7773
|
+
}
|
|
7774
|
+
queue.push({ dir: rootCanonical, depth: 0 });
|
|
7775
|
+
const visited = /* @__PURE__ */ new Set([toComparablePath2(normalizePath2(rootCanonical))]);
|
|
7776
|
+
while (queue.length > 0) {
|
|
7777
|
+
const current = queue.shift();
|
|
7778
|
+
if (!current) {
|
|
7779
|
+
continue;
|
|
7780
|
+
}
|
|
7781
|
+
const { dir, depth } = current;
|
|
7782
|
+
if (isUnityProjectRoot(dir)) {
|
|
7783
|
+
return normalizePath2(dir);
|
|
7784
|
+
}
|
|
7785
|
+
const canDescend = maxDepth === -1 || depth < maxDepth;
|
|
7786
|
+
if (!canDescend) {
|
|
7787
|
+
continue;
|
|
7788
|
+
}
|
|
7789
|
+
const children = listSubdirectoriesSorted(dir);
|
|
7790
|
+
for (const child of children) {
|
|
7791
|
+
let childCanonical = child;
|
|
7792
|
+
try {
|
|
7793
|
+
const stat = (0, import_node_fs2.lstatSync)(child);
|
|
7794
|
+
if (stat.isSymbolicLink()) {
|
|
7795
|
+
try {
|
|
7796
|
+
childCanonical = (0, import_node_fs2.realpathSync)(child);
|
|
7797
|
+
} catch {
|
|
7798
|
+
continue;
|
|
7799
|
+
}
|
|
7800
|
+
}
|
|
7801
|
+
} catch {
|
|
7802
|
+
continue;
|
|
7803
|
+
}
|
|
7804
|
+
const key = toComparablePath2(normalizePath2(childCanonical));
|
|
7805
|
+
if (visited.has(key)) {
|
|
7806
|
+
continue;
|
|
7807
|
+
}
|
|
7808
|
+
visited.add(key);
|
|
7809
|
+
queue.push({ dir: childCanonical, depth: depth + 1 });
|
|
7810
|
+
}
|
|
7811
|
+
}
|
|
7812
|
+
return void 0;
|
|
7813
|
+
}
|
|
7814
|
+
function launch(opts) {
|
|
7815
|
+
const { projectPath, platform, unityArgs, unityVersion } = opts;
|
|
7816
|
+
const unityPath = getUnityPath(unityVersion);
|
|
7817
|
+
console.log(`Detected Unity version: ${unityVersion}`);
|
|
7818
|
+
if (!(0, import_node_fs2.existsSync)(unityPath)) {
|
|
7819
|
+
throw new Error(`Unity ${unityVersion} not found at ${unityPath}. Please install Unity through Unity Hub.`);
|
|
7820
|
+
}
|
|
7821
|
+
console.log("Opening Unity...");
|
|
7822
|
+
console.log(`Project Path: ${projectPath}`);
|
|
7823
|
+
const args = ["-projectPath", projectPath];
|
|
7824
|
+
const unityArgsContainBuildTarget = hasBuildTargetArg(unityArgs);
|
|
7825
|
+
if (platform && platform.length > 0 && !unityArgsContainBuildTarget) {
|
|
7826
|
+
args.push("-buildTarget", platform);
|
|
7827
|
+
}
|
|
7828
|
+
if (unityArgs.length > 0) {
|
|
7829
|
+
args.push(...unityArgs);
|
|
7830
|
+
}
|
|
7831
|
+
const child = (0, import_node_child_process.spawn)(unityPath, args, { stdio: "ignore", detached: true });
|
|
7832
|
+
child.unref();
|
|
7833
|
+
}
|
|
7834
|
+
|
|
7835
|
+
// src/commands/launch.ts
|
|
7836
|
+
function registerLaunchCommand(program3) {
|
|
7837
|
+
program3.command("launch").description("Launch Unity project with matching Editor version").argument("[project-path]", "Path to Unity project").option("-r, --restart", "Kill running Unity and restart").option("-p, --platform <platform>", "Build target (e.g., Android, iOS)").option("--max-depth <n>", "Search depth when project-path is omitted", "3").option("-a, --add-unity-hub", "Add to Unity Hub (does not launch)").option("-f, --favorite", "Add to Unity Hub as favorite (does not launch)").action(async (projectPath, options) => {
|
|
7838
|
+
await runLaunchCommand(projectPath, options);
|
|
7839
|
+
});
|
|
7840
|
+
}
|
|
7841
|
+
function parseMaxDepth(value) {
|
|
7842
|
+
if (value === void 0) {
|
|
7843
|
+
return 3;
|
|
7844
|
+
}
|
|
7845
|
+
const parsed = parseInt(value, 10);
|
|
7846
|
+
if (Number.isNaN(parsed)) {
|
|
7847
|
+
console.error(`Error: Invalid --max-depth value: "${value}". Must be an integer.`);
|
|
7848
|
+
process.exit(1);
|
|
7849
|
+
}
|
|
7850
|
+
return parsed;
|
|
7851
|
+
}
|
|
7852
|
+
async function runLaunchCommand(projectPath, options) {
|
|
7853
|
+
const maxDepth = parseMaxDepth(options.maxDepth);
|
|
7854
|
+
let resolvedProjectPath = projectPath ? (0, import_path6.resolve)(projectPath) : void 0;
|
|
7855
|
+
if (!resolvedProjectPath) {
|
|
7856
|
+
const searchRoot = process.cwd();
|
|
7857
|
+
const depthInfo = maxDepth === -1 ? "unlimited" : String(maxDepth);
|
|
7858
|
+
console.log(
|
|
7859
|
+
`No project-path provided. Searching under ${searchRoot} (max-depth: ${depthInfo})...`
|
|
7860
|
+
);
|
|
7861
|
+
const found = findUnityProjectBfs(searchRoot, maxDepth);
|
|
7862
|
+
if (!found) {
|
|
7863
|
+
console.error(`Error: Unity project not found under ${searchRoot}.`);
|
|
7864
|
+
process.exit(1);
|
|
7865
|
+
}
|
|
7866
|
+
console.log(`Selected project: ${found}`);
|
|
7867
|
+
resolvedProjectPath = found;
|
|
7868
|
+
}
|
|
7869
|
+
const unityVersion = getUnityVersion(resolvedProjectPath);
|
|
7870
|
+
const unityHubOnlyMode = options.addUnityHub === true || options.favorite === true;
|
|
7871
|
+
if (unityHubOnlyMode) {
|
|
7872
|
+
console.log(`Detected Unity version: ${unityVersion}`);
|
|
7873
|
+
console.log(`Project Path: ${resolvedProjectPath}`);
|
|
7874
|
+
const now2 = /* @__PURE__ */ new Date();
|
|
7875
|
+
await ensureProjectEntryAndUpdate(
|
|
7876
|
+
resolvedProjectPath,
|
|
7877
|
+
unityVersion,
|
|
7878
|
+
now2,
|
|
7879
|
+
options.favorite === true
|
|
7880
|
+
);
|
|
7881
|
+
console.log("Unity Hub entry updated.");
|
|
7882
|
+
return;
|
|
7883
|
+
}
|
|
7884
|
+
if (options.restart === true) {
|
|
7885
|
+
await killRunningUnity(resolvedProjectPath);
|
|
7886
|
+
} else {
|
|
7887
|
+
const runningProcess = await findRunningUnityProcess(resolvedProjectPath);
|
|
7888
|
+
if (runningProcess) {
|
|
7889
|
+
console.log(
|
|
7890
|
+
`Unity process already running for project: ${resolvedProjectPath} (PID: ${runningProcess.pid})`
|
|
7891
|
+
);
|
|
7892
|
+
await focusUnityProcess(runningProcess.pid);
|
|
7893
|
+
return;
|
|
7894
|
+
}
|
|
7895
|
+
}
|
|
7896
|
+
await handleStaleLockfile(resolvedProjectPath);
|
|
7897
|
+
const resolved = {
|
|
7898
|
+
projectPath: resolvedProjectPath,
|
|
7899
|
+
platform: options.platform,
|
|
7900
|
+
unityArgs: [],
|
|
7901
|
+
unityVersion
|
|
7902
|
+
};
|
|
7903
|
+
launch(resolved);
|
|
7904
|
+
const now = /* @__PURE__ */ new Date();
|
|
7905
|
+
await updateLastModifiedIfExists(resolvedProjectPath, now);
|
|
7906
|
+
}
|
|
7907
|
+
|
|
7908
|
+
// src/commands/focus-window.ts
|
|
7909
|
+
function registerFocusWindowCommand(program3) {
|
|
7910
|
+
program3.command("focus-window").description("Bring Unity Editor window to front using OS-level commands").action(async () => {
|
|
7911
|
+
const projectRoot = findUnityProjectRoot();
|
|
7912
|
+
if (projectRoot === null) {
|
|
7913
|
+
console.error(
|
|
7914
|
+
JSON.stringify({
|
|
7915
|
+
Success: false,
|
|
7916
|
+
Message: "Unity project not found"
|
|
7917
|
+
})
|
|
7918
|
+
);
|
|
7919
|
+
process.exit(1);
|
|
7920
|
+
}
|
|
7921
|
+
const runningProcess = await findRunningUnityProcess(projectRoot);
|
|
7922
|
+
if (!runningProcess) {
|
|
7923
|
+
console.error(
|
|
7924
|
+
JSON.stringify({
|
|
7925
|
+
Success: false,
|
|
7926
|
+
Message: "No running Unity process found for this project"
|
|
7927
|
+
})
|
|
7928
|
+
);
|
|
7929
|
+
process.exit(1);
|
|
7930
|
+
}
|
|
7931
|
+
try {
|
|
7932
|
+
await focusUnityProcess(runningProcess.pid);
|
|
7933
|
+
console.log(
|
|
7934
|
+
JSON.stringify({
|
|
7935
|
+
Success: true,
|
|
7936
|
+
Message: `Unity Editor window focused (PID: ${runningProcess.pid})`
|
|
7937
|
+
})
|
|
7938
|
+
);
|
|
7939
|
+
} catch (error) {
|
|
7940
|
+
console.error(
|
|
7941
|
+
JSON.stringify({
|
|
7942
|
+
Success: false,
|
|
7943
|
+
Message: `Failed to focus Unity window: ${error instanceof Error ? error.message : String(error)}`
|
|
7944
|
+
})
|
|
7945
|
+
);
|
|
7946
|
+
process.exit(1);
|
|
7947
|
+
}
|
|
7948
|
+
});
|
|
7949
|
+
}
|
|
7950
|
+
|
|
7253
7951
|
// src/cli.ts
|
|
7254
|
-
var BUILTIN_COMMANDS = [
|
|
7952
|
+
var BUILTIN_COMMANDS = [
|
|
7953
|
+
"list",
|
|
7954
|
+
"sync",
|
|
7955
|
+
"completion",
|
|
7956
|
+
"update",
|
|
7957
|
+
"fix",
|
|
7958
|
+
"skills",
|
|
7959
|
+
"launch",
|
|
7960
|
+
"focus-window"
|
|
7961
|
+
];
|
|
7255
7962
|
var program2 = new Command();
|
|
7256
7963
|
program2.name("uloop").description("Unity MCP CLI - Direct communication with Unity Editor").version(VERSION, "-v, --version", "Output the version number");
|
|
7257
7964
|
program2.option("--list-commands", "List all command names (for shell completion)");
|
|
@@ -7272,7 +7979,12 @@ program2.command("fix").description("Clean up stale lock files that may prevent
|
|
|
7272
7979
|
cleanupLockFiles();
|
|
7273
7980
|
});
|
|
7274
7981
|
registerSkillsCommand(program2);
|
|
7982
|
+
registerLaunchCommand(program2);
|
|
7983
|
+
registerFocusWindowCommand(program2);
|
|
7275
7984
|
function registerToolCommand(tool) {
|
|
7985
|
+
if (BUILTIN_COMMANDS.includes(tool.name)) {
|
|
7986
|
+
return;
|
|
7987
|
+
}
|
|
7276
7988
|
const cmd = program2.command(tool.name).description(tool.description);
|
|
7277
7989
|
const properties = tool.inputSchema.properties;
|
|
7278
7990
|
for (const [propName, propInfo] of Object.entries(properties)) {
|
|
@@ -7471,7 +8183,7 @@ async function runWithErrorHandling(fn) {
|
|
|
7471
8183
|
}
|
|
7472
8184
|
function detectShell() {
|
|
7473
8185
|
const shell = process.env["SHELL"] || "";
|
|
7474
|
-
const shellName = (0,
|
|
8186
|
+
const shellName = (0, import_path7.basename)(shell).replace(/\.exe$/i, "");
|
|
7475
8187
|
if (shellName === "zsh") {
|
|
7476
8188
|
return "zsh";
|
|
7477
8189
|
}
|
|
@@ -7486,12 +8198,12 @@ function detectShell() {
|
|
|
7486
8198
|
function getShellConfigPath(shell) {
|
|
7487
8199
|
const home = (0, import_os2.homedir)();
|
|
7488
8200
|
if (shell === "zsh") {
|
|
7489
|
-
return (0,
|
|
8201
|
+
return (0, import_path7.join)(home, ".zshrc");
|
|
7490
8202
|
}
|
|
7491
8203
|
if (shell === "powershell") {
|
|
7492
|
-
return (0,
|
|
8204
|
+
return (0, import_path7.join)(home, "Documents", "WindowsPowerShell", "Microsoft.PowerShell_profile.ps1");
|
|
7493
8205
|
}
|
|
7494
|
-
return (0,
|
|
8206
|
+
return (0, import_path7.join)(home, ".bashrc");
|
|
7495
8207
|
}
|
|
7496
8208
|
function getCompletionScript(shell) {
|
|
7497
8209
|
if (shell === "bash") {
|
|
@@ -7628,10 +8340,10 @@ function cleanupLockFiles() {
|
|
|
7628
8340
|
console.error("Could not find Unity project root.");
|
|
7629
8341
|
process.exit(1);
|
|
7630
8342
|
}
|
|
7631
|
-
const tempDir = (0,
|
|
8343
|
+
const tempDir = (0, import_path7.join)(projectRoot, "Temp");
|
|
7632
8344
|
let cleaned = 0;
|
|
7633
8345
|
for (const lockFile of LOCK_FILES) {
|
|
7634
|
-
const lockPath = (0,
|
|
8346
|
+
const lockPath = (0, import_path7.join)(tempDir, lockFile);
|
|
7635
8347
|
if ((0, import_fs6.existsSync)(lockPath)) {
|
|
7636
8348
|
(0, import_fs6.unlinkSync)(lockPath);
|
|
7637
8349
|
console.log(`Removed: ${lockFile}`);
|
|
@@ -7668,7 +8380,7 @@ function handleCompletion(install, shellOverride) {
|
|
|
7668
8380
|
return;
|
|
7669
8381
|
}
|
|
7670
8382
|
const configPath = getShellConfigPath(shell);
|
|
7671
|
-
const configDir = (0,
|
|
8383
|
+
const configDir = (0, import_path7.dirname)(configPath);
|
|
7672
8384
|
if (!(0, import_fs6.existsSync)(configDir)) {
|
|
7673
8385
|
(0, import_fs6.mkdirSync)(configDir, { recursive: true });
|
|
7674
8386
|
}
|