UNPKG

launch-ide

Version:

Automatically recognize the editor by running processes and open the specified file in it.

583 lines (582 loc) 17.4 kB
var L = Object.defineProperty, W = Object.defineProperties; var $ = Object.getOwnPropertyDescriptors; var B = Object.getOwnPropertySymbols; var F = Object.prototype.hasOwnProperty, H = Object.prototype.propertyIsEnumerable; var A = (t, e, n) => e in t ? L(t, e, { enumerable: !0, configurable: !0, writable: !0, value: n }) : t[e] = n, T = (t, e) => { for (var n in e || (e = {})) F.call(e, n) && A(t, n, e[n]); if (B) for (var n of B(e)) H.call(e, n) && A(t, n, e[n]); return t; }, _ = (t, e) => W(t, $(e)); import w from "fs"; import y from "path"; import O from "child_process"; import V from "os"; import C from "chalk"; import X from "dotenv"; const j = { "/Cursor.app/Contents/MacOS/Cursor": "/Cursor.app/Contents/MacOS/Cursor", "/Comate.app/Contents/MacOS/Electron": "/Comate.app/Contents/MacOS/Electron", "/Windsurf.app/Contents/MacOS/Electron": "/Windsurf.app/Contents/MacOS/Electron", "/Trae.app/Contents/MacOS/Electron": "/Trae.app/Contents/MacOS/Electron", "/Trae CN.app/Contents/MacOS/Electron": "/Trae CN.app/Contents/MacOS/Electron", "/Applications/CodeBuddy.app/Contents/MacOS/Electron": "/Applications/CodeBuddy.app/Contents/MacOS/Electron", "/Visual Studio Code.app/Contents/MacOS/Electron": "/Visual Studio Code.app/Contents/MacOS/Electron", "/Visual Studio Code - Insiders.app/Contents/MacOS/Electron": "/Visual Studio Code - Insiders.app/Contents/MacOS/Electron", "/VSCodium.app/Contents/MacOS/Electron": "/VSCodium.app/Contents/MacOS/Electron", "/WebStorm.app/Contents/MacOS/webstorm": "/WebStorm.app/Contents/MacOS/webstorm", "/HBuilderX.app/Contents/MacOS/HBuilderX": "/HBuilderX.app/Contents/MacOS/HBuilderX", "/Atom.app/Contents/MacOS/Atom": "atom", "/Atom Beta.app/Contents/MacOS/Atom Beta": "/Atom Beta.app/Contents/MacOS/Atom Beta", "/Brackets.app/Contents/MacOS/Brackets": "brackets", "/Sublime Text.app/Contents/MacOS/Sublime Text": "/Sublime Text.app/Contents/SharedSupport/bin/subl", "/Sublime Text.app/Contents/MacOS/sublime_text": "/Sublime Text.app/Contents/SharedSupport/bin/subl", "/Sublime Text 2.app/Contents/MacOS/Sublime Text 2": "/Sublime Text 2.app/Contents/SharedSupport/bin/subl", "/Sublime Text Dev.app/Contents/MacOS/Sublime Text": "/Sublime Text Dev.app/Contents/SharedSupport/bin/subl", "/PhpStorm.app/Contents/MacOS/phpstorm": "/PhpStorm.app/Contents/MacOS/phpstorm", "/PyCharm.app/Contents/MacOS/pycharm": "/PyCharm.app/Contents/MacOS/pycharm", "/PyCharm CE.app/Contents/MacOS/pycharm": "/PyCharm CE.app/Contents/MacOS/pycharm", "/IntelliJ IDEA.app/Contents/MacOS/idea": "/IntelliJ IDEA.app/Contents/MacOS/idea", "/IntelliJ IDEA Ultimate.app/Contents/MacOS/idea": "/IntelliJ IDEA Ultimate.app/Contents/MacOS/idea", "/IntelliJ IDEA Community Edition.app/Contents/MacOS/idea": "/IntelliJ IDEA Community Edition.app/Contents/MacOS/idea", "/Zed.app/Contents/MacOS/zed": "zed", "/GoLand.app/Contents/MacOS/goland": "/GoLand.app/Contents/MacOS/goland", "/AppCode.app/Contents/MacOS/appcode": "/AppCode.app/Contents/MacOS/appcode", "/CLion.app/Contents/MacOS/clion": "/CLion.app/Contents/MacOS/clion", "/RubyMine.app/Contents/MacOS/rubymine": "/RubyMine.app/Contents/MacOS/rubymine", "/MacVim.app/Contents/MacOS/MacVim": "mvim", "/Rider.app/Contents/MacOS/rider": "/Rider.app/Contents/MacOS/rider" }, J = { cursor: ["/Cursor.app/Contents/MacOS/Cursor"], comate: ["/Comate.app/Contents/MacOS/Electron"], windsurf: ["/Windsurf.app/Contents/MacOS/Electron"], trae: [ "/Trae.app/Contents/MacOS/Electron", "/Trae CN.app/Contents/MacOS/Electron" ], codebuddy: ["/Applications/CodeBuddy.app/Contents/MacOS/Electron"], code: ["/Visual Studio Code.app/Contents/MacOS/Electron"], "code-insiders": [ "/Visual Studio Code - Insiders.app/Contents/MacOS/Electron" ], webstorm: ["/WebStorm.app/Contents/MacOS/webstorm"], atom: ["/Atom.app/Contents/MacOS/Atom"], hbuilder: ["/HBuilderX.app/Contents/MacOS/HBuilderX"], phpstorm: ["/PhpStorm.app/Contents/MacOS/phpstorm"], pycharm: ["/PyCharm.app/Contents/MacOS/pycharm"], idea: ["/IntelliJ IDEA.app/Contents/MacOS/idea"], codium: ["/VSCodium.app/Contents/MacOS/Electron"], goland: ["/GoLand.app/Contents/MacOS/goland"], colin: ["/CLion.app/Contents/MacOS/clion"], appcode: ["/AppCode.app/Contents/MacOS/appcode"], "atom-beta": ["/Atom Beta.app/Contents/MacOS/Atom Beta"], brackets: ["/Brackets.app/Contents/MacOS/Brackets"], rider: ["/Rider.app/Contents/MacOS/rider"], rubymine: ["/RubyMine.app/Contents/MacOS/rubymine"], sublime: ["/Sublime Text.app/Contents/MacOS/sublime_text"], zed: ["/Zed.app/Contents/MacOS/zed"] }, U = { cursor: "cursor", windsurf: "windsurf", code: "code", vscodium: "vscodium", codium: "codium", webstorm: "webstorm", "webstorm.sh": "webstorm", hbuilderx: "hbuilderx", "hbuilderx.sh": "hbuilderx", atom: "atom", Brackets: "brackets", "code-insiders": "code-insiders", emacs: "emacs", gvim: "gvim", idea: "idea", "idea.sh": "idea", phpstorm: "phpstorm", "phpstorm.sh": "phpstorm", pycharm: "pycharm", "pycharm.sh": "pycharm", rubymine: "rubymine", "rubymine.sh": "rubymine", sublime_text: "subl", vim: "vim", goland: "goland", "goland.sh": "goland", rider: "rider", "rider.sh": "rider" }, z = { code: ["code"], "code-insiders": ["code-insiders"], webstorm: ["webstorm", "webstorm.sh"], cursor: ["cursor"], windsurf: ["windsurf"], atom: ["atom"], hbuilder: ["hbuilderx", "hbuilderx.sh"], phpstorm: ["phpstorm", "phpstorm.sh"], pycharm: ["pycharm", "pycharm.sh"], idea: ["idea", "idea.sh"], codium: ["vscodium"], goland: ["goland"], brackets: ["Brackets"], rider: ["rider"], rubymine: ["rubymine", "rubymine.sh"], sublime: ["sublime_text"], vim: ["vim"], emacs: ["emacs"] }, G = { "Cursor.exe": "", "Windsurf.exe": "", "Trae.exe": "", "Trae CN.exe": "", "comate.exe": "", "CodeBuddy.exe": "", "Code.exe": "", "Code - Insiders.exe": "", "VSCodium.exe": "", "webstorm.exe": "", "webstorm64.exe": "", "HBuilderX.exe": "", "HBuilderX64.exe": "", "HBuilder.exe": "", "HBuilder64.exe": "", "Brackets.exe": "", "atom.exe": "", "sublime_text.exe": "", "notepad++.exe": "", "clion.exe": "", "clion64.exe": "", "idea.exe": "", "idea64.exe": "", "phpstorm.exe": "", "phpstorm64.exe": "", "pycharm.exe": "", "pycharm64.exe": "", "rubymine.exe": "", "rubymine64.exe": "", "goland.exe": "", "goland64.exe": "", "rider.exe": "", "rider64.exe": "" }, Z = { code: ["Code.exe"], "code-insiders": ["Code - Insiders.exe"], webstorm: ["webstorm.exe", "webstorm64.exe"], cursor: ["Cursor.exe"], windsurf: ["Windsurf.exe"], trae: ["Trae.exe", "Trae CN.exe"], comate: ["comate.exe"], codebuddy: ["CodeBuddy.exe"], atom: ["atom.exe"], hbuilder: [ "HBuilderX.exe", "HBuilder.exe", "HBuilderX64.exe", "HBuilder64.exe" ], phpstorm: ["phpstorm.exe", "phpstorm64.exe"], pycharm: ["pycharm.exe", "pycharm64.exe"], idea: ["idea.exe", "idea64.exe"], codium: ["VSCodium.exe"], goland: ["goland.exe", "goland64.exe"], colin: ["clion.exe", "clion64.exe"], brackets: ["Brackets.exe"], rider: ["rider.exe", "rider64.exe"], rubymine: ["rubymine.exe", "rubymine64.exe"], sublime: ["sublime_text.exe"], notepad: ["notepad++.exe"] }, k = { darwin: j, linux: U, win32: G }, I = { darwin: J, linux: z, win32: Z }, m = "{file}", u = "{line}", M = "{column}"; function Q(t, e, n, o) { let r = "".concat(t, ":").concat(e, ":").concat(n); if (typeof o == "string") r = o.replace(m, t).replace(u, e.toString()).replace(M, n.toString()); else if (o instanceof Array) return o.map((l) => l.replace(m, t).replace(u, e.toString()).replace(M, n.toString())); return [r]; } function K(t) { const { processName: e, fileName: n, lineNumber: o, colNumber: r, workspace: l, openWindowParams: c, pathFormat: i } = t, p = { editorBasename: q(e), openWindowParams: c, workspace: l }, d = Y(p) || "{file}"; return Q(n, o, r, i || d); } function q(t) { let e = y.basename(t).replace(/\.(exe|cmd|bat|sh)$/i, ""); const n = process.platform, o = Object.keys(I[n]); for (let r = 0; r < o.length; r++) if ((I[n][o[r]] || []).some((c) => t.endsWith(c))) { e = o[r]; break; } return e.toLowerCase(); } function Y(t) { const { editorBasename: e, openWindowParams: n, workspace: o } = t; switch (e) { case "atom": case "atom beta": case "subl": case "sublime": case "sublime_text": case "wstorm": case "charm": case "zed": return "".concat(m, ":").concat(u, ":").concat(M); case "notepad++": return ["-n" + u, "-c" + M, m]; case "vim": case "mvim": return ["+call cursor(".concat(u, ", ").concat(M, ")"), m]; case "joe": case "gvim": return ["+" + u, m]; case "emacs": case "emacsclient": return ["+" + u + ":" + M, m]; case "rmate": case "mate": case "mine": return ["--line", u, m]; case "code": case "code-insiders": case "code - insiders": case "codium": case "cursor": case "windsurf": case "trae": case "codebuddy": case "comate": case "vscodium": case "hbuilderx": case "hbuilder": return [ ...o ? [o] : [], "-g", ...n ? [n] : [], "".concat(m, ":").concat(u, ":").concat(M) ]; case "appcode": case "clion": case "clion64": case "idea": case "idea64": case "phpstorm": case "phpstorm64": case "pycharm": case "pycharm64": case "rubymine": case "rubymine64": case "webstorm": case "webstorm64": case "goland": case "goland64": case "rider": case "rider64": return [ ...o ? [o] : [], "--line", u, m ]; } return ""; } function R(t, e) { if (process.env[t]) return process.env[t]; let n = ""; if (e) { const o = y.resolve(e, ".env.local"); w.existsSync(o) && (n = o); } if (!n) { const o = y.resolve(process.cwd(), ".env.local"); w.existsSync(o) && (n = o); } if (n) { const o = w.readFileSync(n, "utf-8"); return X.parse(o || "")[t]; } return null; } const ee = { darwin: "ps ax -o comm=", linux: "ps -eo comm --sort=comm", // wmic's performance is better, but window11 not build in win32: 'wmic process where "executablepath is not null" get executablepath' }, te = 'powershell -NoProfile -Command "Get-CimInstance -Query \\"select executablepath from win32_process where executablepath is not null\\" | % { $_.ExecutablePath }"'; function ne(t, e) { let n = null; const o = R("CODE_EDITOR", e || ""); if (o) { const r = N(o); if (r) n = r; else return [o]; } if (!n && t) { const r = N(t); r && (n = r); } if (!n) { const r = oe(); if (r) return [r]; } try { let r; const l = process.platform, c = process.platform === "win32", i = ee[l], h = k[l]; v(c); let p = ""; try { p = O.execSync(i, { encoding: "utf-8" }); } catch (S) { c && (p = O.execSync(te, { encoding: "utf-8" })); } const d = Object.keys(h), E = p.split(c ? "\r\n" : "\n").map((S) => S.trim()); for (let S = 0; S < d.length; S++) { const s = d[S]; let f = "", x = ""; if (c) { const a = E.find( (g) => y.basename(g).toLowerCase() === s.toLowerCase() ); a && (x = y.basename(a), f = a); } else if (l === "darwin") { const a = E.find( (g) => g.toLowerCase().endsWith(s.toLowerCase()) ); if (a) { const g = a.replace(s, ""), P = h[s]; x = s, P.includes("/") ? f = "".concat(g).concat(P) : f = P; } } else p.indexOf(s) !== -1 && (x = s, f = h[s]); if (x && f) { if (n != null && n.includes(x)) return [f]; r || (r = [f]); } } if (r) return r; } catch (r) { } return process.env.VISUAL ? [process.env.VISUAL] : process.env.EDITOR ? [process.env.EDITOR] : [null]; } const N = (t) => { const e = process.platform; return I[e] && I[e][t] || null; }, v = (t) => { if (t) try { O.execSync("chcp 65001"); } catch (e) { } }; function oe() { const t = process.platform, e = Object.keys(k[t]); try { return re(process.pid, t, e); } catch (n) { return console.error("Error while getting editor by PID:", n), null; } } function re(t, e, n) { let o = 0; const r = 50, l = 0; for (; t && t !== l && o < r; ) { const c = se(t, e); if (!c) break; const { command: i, parentPid: h } = c; if (de(i, n)) return i; t = h, o++; } return null; } function se(t, e) { switch (e) { case "darwin": case "linux": return ae(t); case "win32": return ce(t); default: return null; } } function ae(t) { try { const n = O.execSync("ps -p ".concat(t, " -o ppid=,comm="), { encoding: "utf8" }).trim().split("\n"); return n.length ? le(n[0].trim()) : null; } catch (e) { return null; } } function ce(t) { return ie(t) || pe(t); } function ie(t) { try { v(!0); const n = O.execSync( 'wmic process where "ProcessId='.concat(t, '" get ParentProcessId,ExecutablePath /format:csv'), { encoding: "utf8" } ).trim().split("\r\n").filter((r) => r.trim()).slice(1); if (n.length === 0) return null; const o = n[0].split(","); return o.length < 3 ? null : { command: o[1].trim(), parentPid: parseInt(o[2].trim()) }; } catch (e) { return null; } } function pe(t) { try { v(!0); const n = O.execSync( 'powershell -NoProfile -Command "Get-CimInstance -Query "select ParentProcessId,ExecutablePath from win32_process where ProcessId='.concat(t, "\" | ForEach-Object { $_.ExecutablePath + ',' + $_.ParentProcessId }\""), { encoding: "utf8" } ).trim(); if (!n) return null; const o = n.split(","); return o.length < 2 ? null : { command: o[0].trim(), parentPid: parseInt(o[1].trim()) }; } catch (e) { return null; } } function le(t) { const e = t.match(/^(\d+)\s+(.+)$/); return e ? { command: e[2], parentPid: parseInt(e[1]) } : null; } function de(t, e) { return e.some( (n) => t.toLowerCase().endsWith(n.toLowerCase()) ); } function me(t) { switch (t) { case "vim": case "emacs": case "nano": return !0; } return !1; } function ue(t) { const e = R( "CODE_INSPECTOR_FORMAT_PATH", t ); if (e) try { return JSON.parse(e); } catch (n) { return null; } return null; } function D(t, e) { console.log( C.red("Could not open " + y.basename(t) + " in the editor.") ), e && (e[e.length - 1] !== "." && (e += "."), console.log( C.red("The editor process exited with an error: " + e) )), console.log( "To set up the editor integration, add something like " + C.cyan("CODE_EDITOR=code") + " to the " + C.green(".env.local") + " file in your project folder, or add " + C.green('editor: "code"') + " to CodeInspectorPlugin config, and then restart the development server. Learn more: " + C.green("https://goo.gl/MMTaZt") ); } let b = null; function Ce(t) { return t === "reuse" ? "-r" : t === "new" ? "-n" : ""; } function ye(t) { let { file: e, line: n = 1, column: o = 1, editor: r, method: l, format: c, onError: i, rootDir: h } = t; if (!w.existsSync(e)) return; let [p, ...d] = ne(r, h); const E = ue(h || "") || c; if (!p || p.toLowerCase() === "none") { typeof i == "function" ? i(e, "Failed to recognize IDE automatically") : console.log( "Failed to recognize IDE automatically, add something like " + C.cyan("CODE_EDITOR=code") + " to the " + C.green(".env.local") + " file in your project folder, or add " + C.green('editor: "code"') + " to CodeInspectorPlugin config, and then restart the development server. Learn more: " + C.green("https://goo.gl/MMTaZt") ); return; } process.platform === "linux" && e.startsWith("/mnt/") && /Microsoft/i.test(V.release()) && (e = y.relative("", e)); let S = null; if (n ? d = d.concat( K({ processName: p, fileName: e, lineNumber: n, colNumber: o, workspace: S, openWindowParams: Ce(l), pathFormat: E }) ) : d.push(e), b && me(p) && b.kill("SIGKILL"), process.platform === "win32") { const s = (a) => a.replace(/([&|<>,;=^])/g, "^$1"), f = (a) => a.includes("^") ? '^"'.concat(a, '^"') : a.includes(" ") ? '"'.concat(a, '"') : a, x = [p, ...d.map(s)].map(f).join(" "); b = O.exec(x, { stdio: "inherit", // @ts-ignore shell: !0, env: _(T({}, process.env), { NODE_OPTIONS: "" }) }); } else b = O.spawn(p, d, { stdio: "inherit", env: _(T({}, process.env), { NODE_OPTIONS: "" }) }); b.on("exit", function(s) { b = null, s && (typeof i == "function" ? i(e, "(code " + s + ")") : D(e, "(code " + s + ")")); }), b.on("error", function(s) { typeof i == "function" ? i(e, s.message) : D(e, s.message); }); } export { Q as formatOpenPath, R as getEnvVariable, ye as launchIDE };