@m0x373/pimpt 0.1.0 → 0.1.2

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/README.md ADDED
@@ -0,0 +1,105 @@
1
+ # pimpt
2
+
3
+ An interactive setup assistant for Windows Terminal. Choose settings and PowerShell features from a guided menu, review the summary, and confirm before changes are applied.
4
+
5
+ ## Requirements
6
+
7
+ - Windows 10 or later
8
+ - Windows Terminal
9
+ - Node.js 22 or later
10
+ - PowerShell for PowerShell profile features
11
+
12
+ Some optional features install modules from the PowerShell Gallery or download a font, so an internet connection may be required.
13
+
14
+ ## Install
15
+
16
+ ```powershell
17
+ npm install --global @m0x373/pimpt
18
+ ```
19
+
20
+ Then start the installer:
21
+
22
+ ```powershell
23
+ pimpt
24
+ ```
25
+
26
+ The npm package is scoped because npm does not allow this project to publish under the unscoped name `pimpt`.
27
+
28
+ ## Usage
29
+
30
+ ```text
31
+ pimpt
32
+ pimpt --help
33
+ pimpt --version
34
+ ```
35
+
36
+ The installer detects the Windows Terminal settings file for the Stable, Preview, or Canary release. Select an area, choose settings, review the summary, and confirm to apply the changes.
37
+
38
+ ## Available options
39
+
40
+ ### Appearance and terminal settings
41
+
42
+ - Set window opacity and acrylic effects.
43
+ - Set a background color.
44
+ - Choose a terminal font.
45
+ - Hide the Windows PowerShell startup banner.
46
+ - Enable PowerShell file icons with the Terminal-Icons module and Hack Nerd Font Mono.
47
+
48
+ ### PowerShell features
49
+
50
+ - Set a default starting directory. Relative paths such as `Downloads` resolve from your user folder.
51
+ - Enable a scrollable command history preview with PSReadLine.
52
+ - Enable a colored tree view for `ls`.
53
+
54
+ When tree-style `ls` is enabled, the original `Get-ChildItem` command remains available as `gci`.
55
+
56
+ The tree view defaults to a maximum depth of 4 and 50 displayed entries:
57
+
58
+ ```powershell
59
+ ls
60
+ ls .\src -Depth 2
61
+ ls .\src -Limit 200
62
+ ls .\src -All
63
+ ls .\src -Force
64
+ ```
65
+
66
+ `-All` disables the entry limit and may produce a large amount of output.
67
+
68
+ ## Settings safety
69
+
70
+ - Windows Terminal settings are edited as JSONC, preserving comments and formatting where possible.
71
+ - A backup is created before `settings.json` is changed.
72
+ - The installer asks for confirmation before applying the selected configuration.
73
+ - Existing backups can be restored from the `Other` area.
74
+ - PowerShell features are added to the current user's PowerShell profile in marked blocks.
75
+
76
+ ## Development
77
+
78
+ ```powershell
79
+ npm install
80
+ npm test
81
+ npm run typecheck
82
+ npm run build
83
+ ```
84
+
85
+ ## Publishing
86
+
87
+ Publishing is available manually from the GitHub Actions tab using the
88
+ `Publish to npm` workflow. It checks out the latest commit on `main`, runs the
89
+ typecheck, tests, and build, then publishes the version in `package.json` with
90
+ the `latest` npm tag. If that version is already published, it updates the
91
+ `latest` tag instead of trying to upload the version again.
92
+
93
+ Before running it, add an npm access token with publish permission as the
94
+ repository Actions secret `NPM_TOKEN`. Update the package version in
95
+ `package.json` and `package-lock.json` and push the changes to `main` first.
96
+ Published versions cannot be overwritten, so each publish needs a new version.
97
+
98
+ ## License
99
+
100
+ ISC, as declared in the package metadata.
101
+
102
+ ## Links
103
+
104
+ - [Source repository](https://github.com/M0x37/pimpt)
105
+ - [npm package](https://www.npmjs.com/package/@m0x373/pimpt)
package/dist/index.js CHANGED
File without changes
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/index.ts","../src/installer.ts","../src/settings.ts","../src/fonts.ts","../src/powershell.ts","../src/summary.ts","../src/wtsettings.ts"],"sourcesContent":["#!/usr/bin/env node\n\nimport { readFileSync } from \"node:fs\";\nimport pc from \"picocolors\";\nimport { runInstaller } from \"./installer.js\";\n\nfunction readVersion(): string {\n const pkg = JSON.parse(\n readFileSync(new URL(\"../package.json\", import.meta.url), \"utf8\"),\n ) as { version: string };\n return pkg.version;\n}\n\nfunction printHelp(): void {\n console.log(`\n${pc.bold(pc.cyan(\"pimpt\"))} ${pc.dim(\"— interactive Windows Terminal setup assistant\")}\n\n${pc.bold(\"Usage\")}\n pimpt Start the interactive installer\n pimpt --help Show this help\n pimpt --version Show the installed version\n\n${pc.bold(\"Status\")}\n Preview: preferences are collected, but settings.json is not modified yet.\n`);\n}\n\nasync function main(): Promise<void> {\n const args = process.argv.slice(2);\n\n if (args.includes(\"--help\") || args.includes(\"-h\")) {\n printHelp();\n return;\n }\n\n if (args.includes(\"--version\") || args.includes(\"-v\")) {\n console.log(`pimpt ${readVersion()}`);\n return;\n }\n\n if (args.length > 0) {\n console.error(`Unknown option: ${args[0]}`);\n printHelp();\n process.exitCode = 1;\n return;\n }\n\n await runInstaller();\n}\n\ntry {\n await main();\n} catch (error) {\n console.error(pc.red(\"pimpt failed:\"));\n console.error(error instanceof Error ? error.stack ?? error.message : String(error));\n process.exitCode = 1;\n}\n","import {\r\n cancel,\r\n confirm,\r\n intro,\r\n isCancel,\r\n log,\r\n note,\r\n outro,\r\n select,\r\n spinner,\r\n text,\r\n} from \"@clack/prompts\";\r\nimport { spawn } from \"node:child_process\";\r\nimport { statSync } from \"node:fs\";\r\nimport { parse, type ParseError } from \"jsonc-parser\";\r\nimport { win32 as pathWin32 } from \"node:path\";\r\nimport pc from \"picocolors\";\r\nimport { setTimeout as delay } from \"node:timers/promises\";\r\nimport {\r\n BACKGROUND_CUSTOM,\r\n settings,\r\n type SettingDefinition,\r\n type SettingValue,\r\n} from \"./settings.js\";\r\nimport {\r\n canInstallFont,\r\n installFont,\r\n installNerdFont,\r\n isFontInstalled,\r\n NERD_FONT_FAMILY,\r\n} from \"./fonts.js\";\r\nimport {\r\n addTerminalIconsToPowerShellProfile,\r\n addHistoryPreviewToPowerShellProfile,\r\n addTreeListingToPowerShellProfile,\r\n installPSReadLineModule,\r\n installTerminalIconsModule,\r\n readPowerShellProfileFeatures,\r\n} from \"./powershell.js\";\r\nimport { buildSummarySections, normalizeHex } from \"./summary.js\";\r\nimport {\r\n createSettingsBackup,\r\n findSettingsPath,\r\n InvalidSettingsFileError,\r\n listSettingsBackups,\r\n readSettingsFile,\r\n restoreSettingsBackup,\r\n setSetting,\r\n writeSettingsFile,\r\n} from \"./wtsettings.js\";\r\n\r\nconst BANNER = `\r\n ██████╗ ██╗███╗ ███╗██████╗ ████████╗\r\n ██╔══██╗██║████╗ ████║██╔══██╗╚══██╔══╝\r\n ██████╔╝██║██╔████╔██║██████╔╝ ██║\r\n ██╔═══╝ ██║██║╚██╔╝██║██╔═══╝ ██║\r\n ██║ ██║██║ ╚═╝ ██║██║ ██║\r\n ╚═╝ ╚═╝╚═╝ ╚═╝╚═╝ ╚═╝\r\n`;\r\n\r\nfunction bail<T>(value: T): Exclude<T, symbol> {\r\n if (isCancel(value)) {\r\n cancel(\"Setup cancelled. Nothing was changed.\");\r\n process.exit(0);\r\n }\r\n return value as Exclude<T, symbol>;\r\n}\r\n\r\nclass StartingDirectoryInputError extends Error {}\r\n\r\nfunction normalizeStartingDirectory(value: string): string {\r\n let directory = value.trim();\r\n if (!directory) return \"\";\r\n\r\n if (\r\n (directory.startsWith('\"') && directory.endsWith('\"')) ||\r\n (directory.startsWith(\"'\") && directory.endsWith(\"'\"))\r\n ) {\r\n directory = directory.slice(1, -1).trim();\r\n }\r\n if (!directory) return \"\";\r\n\r\n const userProfile = process.env.USERPROFILE ?? process.env.HOME;\r\n if (/^~(?=$|[\\\\/])/.test(directory)) {\r\n if (!userProfile) {\r\n throw new StartingDirectoryInputError(\r\n \"Cannot resolve '~' because the user folder is unknown.\",\r\n );\r\n }\r\n directory = directory.replace(/^~/, userProfile);\r\n }\r\n\r\n directory = directory.replace(/%([^%]+)%/g, (variable, name: string) => {\r\n const key = Object.keys(process.env).find(\r\n (candidate) => candidate.toLowerCase() === name.toLowerCase(),\r\n );\r\n const environmentValue = key ? process.env[key] : undefined;\r\n if (environmentValue === undefined) {\r\n throw new StartingDirectoryInputError(\r\n `Unknown environment variable in starting path: ${variable}`,\r\n );\r\n }\r\n return environmentValue;\r\n });\r\n\r\n if (/^[a-zA-Z]:(?![\\\\/])/.test(directory)) {\r\n throw new StartingDirectoryInputError(\r\n \"Use an absolute drive path, for example C:\\\\Users\\\\you\\\\Downloads.\",\r\n );\r\n }\r\n\r\n if (/^[\\\\/](?![\\\\/])/.test(directory)) {\r\n if (!userProfile) {\r\n throw new StartingDirectoryInputError(\r\n \"Cannot resolve a rooted path because the user folder is unknown.\",\r\n );\r\n }\r\n directory = pathWin32.resolve(pathWin32.parse(userProfile).root, directory);\r\n }\r\n\r\n if (pathWin32.isAbsolute(directory)) return pathWin32.normalize(directory);\r\n if (!userProfile) {\r\n throw new StartingDirectoryInputError(\r\n \"Cannot resolve a relative starting path because the user folder is unknown.\",\r\n );\r\n }\r\n return pathWin32.resolve(userProfile, directory);\r\n}\r\n\r\nfunction validateStartingDirectory(value: string | undefined): string | undefined {\r\n let directory: string;\r\n try {\r\n directory = normalizeStartingDirectory(value ?? \"\");\r\n } catch (error) {\r\n if (error instanceof StartingDirectoryInputError) return error.message;\r\n throw error;\r\n }\r\n\r\n if (!directory || process.platform !== \"win32\") return undefined;\r\n\r\n try {\r\n if (!statSync(directory).isDirectory()) {\r\n return \"The starting path must be an existing folder.\";\r\n }\r\n } catch (error) {\r\n if (\r\n error !== null &&\r\n typeof error === \"object\" &&\r\n \"code\" in error &&\r\n (error.code === \"ENOENT\" || error.code === \"ENOTDIR\")\r\n ) {\r\n return `Folder not found: ${directory}`;\r\n }\r\n if (\r\n error !== null &&\r\n typeof error === \"object\" &&\r\n \"code\" in error &&\r\n (error.code === \"EACCES\" || error.code === \"EPERM\")\r\n ) {\r\n return `Cannot access folder: ${directory}`;\r\n }\r\n throw error;\r\n }\r\n return undefined;\r\n}\r\n\r\nasync function askSetting(\r\n setting: SettingDefinition,\r\n currentValue?: SettingValue,\r\n): Promise<SettingValue> {\r\n const prompt = setting.prompt;\r\n\r\n if (prompt.kind === \"select\") {\r\n const selectValue = async () =>\r\n bail(\r\n await select<string>({\r\n message: prompt.message,\r\n options: prompt.options,\r\n initialValue: prompt.initialValue,\r\n }),\r\n );\r\n\r\n if (setting.id === \"fontFace\") {\r\n while (true) {\r\n const fontFamily = await selectValue();\r\n if (fontFamily === \"keep\" || isFontInstalled(fontFamily)) {\r\n return fontFamily;\r\n }\r\n\r\n if (!canInstallFont(fontFamily)) {\r\n log.warn(\r\n pc.yellow(\r\n `${fontFamily} is not installed and cannot be installed automatically. Choose another font.`,\r\n ),\r\n );\r\n continue;\r\n }\r\n\r\n const shouldInstall = bail(\r\n await confirm({\r\n message: `${fontFamily} is not installed. Install it now? Select No to choose another font.`,\r\n initialValue: true,\r\n }),\r\n );\r\n if (!shouldInstall) continue;\r\n\r\n const fontSpinner = spinner();\r\n fontSpinner.start(`Installing ${fontFamily}…`);\r\n try {\r\n await installFont(fontFamily);\r\n } catch (error) {\r\n fontSpinner.error(`Could not install ${fontFamily}.`);\r\n throw error;\r\n }\r\n fontSpinner.stop(\r\n `${fontFamily} installed. Restart Windows Terminal to use it.`,\r\n );\r\n return fontFamily;\r\n }\r\n }\r\n\r\n const value = await selectValue();\r\n\r\n // Hintergrundfarbe: bei \"Custom\" folgt eine Hex-Eingabe mit Validierung.\r\n if (setting.id === \"background\" && value === BACKGROUND_CUSTOM) {\r\n const custom = bail(\r\n await text({\r\n message: \"Enter a background color\",\r\n placeholder: \"#1E1E2E\",\r\n initialValue: \"\",\r\n validate: (input) => {\r\n const raw = input ?? \"\";\r\n return /^#?[0-9a-fA-F]{6}$/.test(raw.trim())\r\n ? undefined\r\n : \"Use a 6-digit hex color, e.g. #1E1E2E\";\r\n },\r\n }),\r\n );\r\n return normalizeHex(custom);\r\n }\r\n\r\n return value;\r\n }\r\n\r\n if (prompt.kind === \"text\") {\r\n const value = bail(\r\n await text({\r\n message: prompt.message,\r\n placeholder: prompt.placeholder,\r\n initialValue:\r\n currentValue === undefined ? prompt.initialValue : String(currentValue),\r\n ...(setting.id === \"startingDirectory\"\r\n ? { validate: validateStartingDirectory }\r\n : prompt.validate\r\n ? { validate: prompt.validate }\r\n : {}),\r\n }),\r\n );\r\n return setting.id === \"startingDirectory\"\r\n ? normalizeStartingDirectory(value)\r\n : value;\r\n }\r\n\r\n return bail(\r\n await confirm({\r\n message: prompt.message,\r\n initialValue: prompt.initialValue,\r\n }),\r\n );\r\n}\r\n\r\nfunction renderSummary(answers: Record<string, SettingValue>): void {\r\n const sections = buildSummarySections(answers);\r\n\r\n if (sections.length === 0) {\r\n note(\"No settings selected.\", \"Configuration summary\");\r\n return;\r\n }\r\n\r\n const labelWidth = Math.max(\r\n ...sections.flatMap((section) =>\r\n section.rows.map(([label]) => label.length),\r\n ),\r\n );\r\n\r\n const lines: string[] = [];\r\n\r\n sections.forEach((section, index) => {\r\n if (index > 0) lines.push(\"\");\r\n lines.push(pc.bold(pc.cyan(section.group)));\r\n\r\n for (const [label, value] of section.rows) {\r\n lines.push(` ${pc.dim(label.padEnd(labelWidth))} ${value}`);\r\n }\r\n });\r\n\r\n note(lines.join(\"\\n\"), \"Your configuration\");\r\n}\r\n\r\nfunction openNewTerminalTab(): boolean {\r\n if (!process.env.WT_SESSION) return false;\r\n\r\n try {\r\n const terminal = spawn(\"wt.exe\", [\"-w\", \"0\", \"new-tab\"], {\r\n detached: true,\r\n stdio: \"ignore\",\r\n windowsHide: true,\r\n });\r\n terminal.on(\"error\", (error) => {\r\n log.warn(\r\n pc.yellow(`Could not open a new Windows Terminal tab: ${error.message}`),\r\n );\r\n });\r\n terminal.unref();\r\n return true;\r\n } catch (error) {\r\n log.warn(\r\n pc.yellow(`Could not open a new Windows Terminal tab: ${String(error)}`),\r\n );\r\n return false;\r\n }\r\n}\r\n\r\nfunction getDefaultProfileIndex(content: string): number | undefined {\r\n const parsed = parse(content) as {\r\n defaultProfile?: unknown;\r\n profiles?: { list?: unknown };\r\n };\r\n if (\r\n typeof parsed.defaultProfile !== \"string\" ||\r\n !parsed.profiles ||\r\n typeof parsed.profiles !== \"object\" ||\r\n !Array.isArray(parsed.profiles.list)\r\n ) {\r\n return undefined;\r\n }\r\n\r\n const index = parsed.profiles.list.findIndex(\r\n (profile: unknown) =>\r\n profile !== null &&\r\n typeof profile === \"object\" &&\r\n \"guid\" in profile &&\r\n profile.guid === parsed.defaultProfile,\r\n );\r\n return index < 0 ? undefined : index;\r\n}\r\n\r\nfunction getWindowsPowerShellProfiles(\r\n content: string,\r\n): { index: number; commandline?: string }[] {\r\n const parseErrors: ParseError[] = [];\r\n const parsed: unknown = parse(content, parseErrors, {\r\n allowTrailingComma: true,\r\n });\r\n if (\r\n parseErrors.length > 0 ||\r\n parsed === null ||\r\n typeof parsed !== \"object\" ||\r\n Array.isArray(parsed)\r\n ) {\r\n throw new InvalidSettingsFileError();\r\n }\r\n\r\n const profiles = \"profiles\" in parsed ? parsed.profiles : undefined;\r\n if (\r\n profiles === null ||\r\n typeof profiles !== \"object\" ||\r\n Array.isArray(profiles) ||\r\n !(\"list\" in profiles) ||\r\n !Array.isArray(profiles.list)\r\n ) {\r\n return [];\r\n }\r\n\r\n return profiles.list.flatMap((profile: unknown, index: number) => {\r\n if (\r\n profile === null ||\r\n typeof profile !== \"object\" ||\r\n Array.isArray(profile)\r\n ) {\r\n return [];\r\n }\r\n\r\n const name =\r\n \"name\" in profile && typeof profile.name === \"string\"\r\n ? profile.name\r\n : \"\";\r\n const commandline =\r\n \"commandline\" in profile && typeof profile.commandline === \"string\"\r\n ? profile.commandline\r\n : undefined;\r\n return name.toLowerCase() === \"windows powershell\" ||\r\n /(?:^|[\\\\/\"])powershell\\.exe(?:[\"\\s]|$)/i.test(commandline ?? \"\")\r\n ? [\r\n {\r\n index,\r\n ...(commandline !== undefined ? { commandline } : {}),\r\n },\r\n ]\r\n : [];\r\n });\r\n}\r\n\r\nfunction readConfiguredAnswers(\r\n settingsPath: string | undefined,\r\n): Record<string, SettingValue> {\r\n const answers: Record<string, SettingValue> = {};\r\n try {\r\n const profileFeatures = readPowerShellProfileFeatures();\r\n if (profileFeatures.terminalIcons) answers.terminalIcons = true;\r\n if (profileFeatures.historyPreview) answers.historyPreview = true;\r\n if (profileFeatures.treeListing) answers.treeListing = true;\r\n } catch (error) {\r\n log.warn(\r\n pc.yellow(\r\n `Could not detect configured PowerShell features: ${error instanceof Error ? error.message : String(error)}`,\r\n ),\r\n );\r\n }\r\n if (!settingsPath) return answers;\r\n\r\n const content = readSettingsFile(settingsPath);\r\n const parseErrors: ParseError[] = [];\r\n const parsed: unknown = parse(content, parseErrors, {\r\n allowTrailingComma: true,\r\n });\r\n if (\r\n parseErrors.length > 0 ||\r\n parsed === null ||\r\n typeof parsed !== \"object\" ||\r\n Array.isArray(parsed)\r\n ) {\r\n log.warn(\r\n pc.yellow(\r\n \"Could not read existing settings.json values because the file contains invalid JSONC.\",\r\n ),\r\n );\r\n return answers;\r\n }\r\n\r\n const profiles =\r\n \"profiles\" in parsed && parsed.profiles !== null\r\n ? parsed.profiles\r\n : undefined;\r\n const profileList =\r\n profiles !== null &&\r\n typeof profiles === \"object\" &&\r\n !Array.isArray(profiles) &&\r\n \"list\" in profiles &&\r\n Array.isArray(profiles.list)\r\n ? profiles.list\r\n : [];\r\n const defaultProfileGuid =\r\n \"defaultProfile\" in parsed ? parsed.defaultProfile : undefined;\r\n const defaultProfile =\r\n typeof defaultProfileGuid === \"string\"\r\n ? profileList.find(\r\n (profile: unknown) =>\r\n profile !== null &&\r\n typeof profile === \"object\" &&\r\n !Array.isArray(profile) &&\r\n \"guid\" in profile &&\r\n profile.guid === defaultProfileGuid,\r\n )\r\n : undefined;\r\n const defaults =\r\n profiles !== null &&\r\n typeof profiles === \"object\" &&\r\n !Array.isArray(profiles) &&\r\n \"defaults\" in profiles\r\n ? profiles.defaults\r\n : undefined;\r\n\r\n if (defaults !== null && typeof defaults === \"object\" && !Array.isArray(defaults)) {\r\n if (\r\n \"opacity\" in defaults &&\r\n typeof defaults.opacity === \"number\" &&\r\n Number.isInteger(defaults.opacity) &&\r\n defaults.opacity >= 0 &&\r\n defaults.opacity <= 100\r\n ) {\r\n answers.transparency =\r\n defaults.opacity === 100 &&\r\n \"useAcrylic\" in defaults &&\r\n defaults.useAcrylic === false\r\n ? \"off\"\r\n : String(defaults.opacity);\r\n }\r\n\r\n if (\"background\" in defaults && typeof defaults.background === \"string\") {\r\n answers.background = defaults.background;\r\n }\r\n\r\n const defaultStartingDirectory =\r\n \"startingDirectory\" in defaults &&\r\n typeof defaults.startingDirectory === \"string\"\r\n ? defaults.startingDirectory\r\n : undefined;\r\n const font =\r\n \"font\" in defaults && defaults.font !== null\r\n ? defaults.font\r\n : undefined;\r\n if (\r\n font !== null &&\r\n typeof font === \"object\" &&\r\n !Array.isArray(font) &&\r\n \"face\" in font &&\r\n typeof font.face === \"string\"\r\n ) {\r\n answers.fontFace = font.face;\r\n }\r\n\r\n const profileStartingDirectory =\r\n defaultProfile !== null &&\r\n typeof defaultProfile === \"object\" &&\r\n !Array.isArray(defaultProfile) &&\r\n \"startingDirectory\" in defaultProfile &&\r\n typeof defaultProfile.startingDirectory === \"string\"\r\n ? defaultProfile.startingDirectory\r\n : undefined;\r\n const startingDirectory =\r\n profileStartingDirectory ?? defaultStartingDirectory;\r\n if (startingDirectory !== undefined) {\r\n const error = validateStartingDirectory(startingDirectory);\r\n if (error) {\r\n log.warn(pc.yellow(`Ignoring the saved starting directory: ${error}`));\r\n } else {\r\n answers.startingDirectory =\r\n normalizeStartingDirectory(startingDirectory);\r\n }\r\n }\r\n }\r\n\r\n const powerShellProfiles = getWindowsPowerShellProfiles(content);\r\n if (\r\n powerShellProfiles.length > 0 &&\r\n powerShellProfiles.every((profile) =>\r\n /(?:^|\\s)-NoLogo(?:\\s|$)/i.test(profile.commandline ?? \"\"),\r\n )\r\n ) {\r\n answers.hidePowerShellBanner = true;\r\n }\r\n\r\n return answers;\r\n}\r\n\r\n/**\r\n * Schreibt die Antworten in verfügbare Terminal-Einstellungen. Kommentare und\r\n * Formatierung der JSONC-Dateien werden erhalten.\r\n */\r\nasync function applySettings(\r\n answers: Record<string, SettingValue>,\r\n settingsPath: string | undefined = findSettingsPath(),\r\n): Promise<void> {\r\n const terminalIconsEnabled = answers.terminalIcons === true;\r\n const hidePowerShellBanner = answers.hidePowerShellBanner === true;\r\n\r\n if (!settingsPath) {\r\n if (terminalIconsEnabled) {\r\n throw new Error(\r\n \"Cannot enable PowerShell file icons because Windows Terminal settings.json could not be found.\",\r\n );\r\n }\r\n if (hidePowerShellBanner) {\r\n throw new Error(\r\n \"Cannot hide the PowerShell startup banner because Windows Terminal settings.json could not be found.\",\r\n );\r\n }\r\n log.warn(\r\n pc.dim(\"Could not find Windows Terminal settings.json. Skipping write.\"),\r\n );\r\n return;\r\n }\r\n\r\n log.info(pc.dim(`Writing to ${settingsPath}…`));\r\n\r\n const originalContent = readSettingsFile(settingsPath);\r\n let content = originalContent;\r\n for (const setting of settings) {\r\n const value = answers[setting.id];\r\n if (value === undefined) continue;\r\n if (!setting.jsonPath) continue;\r\n if (setting.skipIfKeep && value === \"keep\") continue;\r\n if (terminalIconsEnabled && setting.id === \"fontFace\") continue;\r\n\r\n if (setting.id === \"transparency\") {\r\n const opacity = value === \"off\" ? 100 : Number(value);\r\n if (!Number.isInteger(opacity) || opacity < 0 || opacity > 100) {\r\n throw new Error(`Invalid transparency value: ${String(value)}`);\r\n }\r\n\r\n content = setSetting(content, setting.jsonPath, opacity);\r\n content = setSetting(\r\n content,\r\n [\"profiles\", \"defaults\", \"useAcrylic\"],\r\n value !== \"off\",\r\n );\r\n content = setSetting(\r\n content,\r\n [\"useAcrylicInTabRow\"],\r\n value !== \"off\",\r\n );\r\n } else if (setting.id === \"background\") {\r\n content = setSetting(content, setting.jsonPath, value);\r\n content = setSetting(\r\n content,\r\n [\"profiles\", \"defaults\", \"tabColor\"],\r\n value,\r\n );\r\n } else if (setting.id === \"fontFace\") {\r\n const defaultProfileIndex = getDefaultProfileIndex(content);\r\n content = setSetting(content, setting.jsonPath, value);\r\n if (defaultProfileIndex !== undefined) {\r\n content = setSetting(\r\n content,\r\n [\"profiles\", \"list\", defaultProfileIndex, \"font\", \"face\"],\r\n value,\r\n );\r\n }\r\n } else if (setting.id === \"startingDirectory\") {\r\n const defaultProfileIndex = getDefaultProfileIndex(content);\r\n const startingDirectory = String(value).trim() || undefined;\r\n content = setSetting(content, setting.jsonPath, startingDirectory);\r\n if (defaultProfileIndex !== undefined) {\r\n content = setSetting(\r\n content,\r\n [\"profiles\", \"list\", defaultProfileIndex, \"startingDirectory\"],\r\n startingDirectory,\r\n );\r\n }\r\n } else {\r\n content = setSetting(content, setting.jsonPath, value);\r\n }\r\n }\r\n\r\n if (hidePowerShellBanner) {\r\n const powerShellProfiles = getWindowsPowerShellProfiles(content);\r\n if (powerShellProfiles.length === 0) {\r\n throw new Error(\r\n \"Cannot hide the PowerShell startup banner because no Windows PowerShell profile was found.\",\r\n );\r\n }\r\n\r\n for (const profile of powerShellProfiles) {\r\n const commandline =\r\n profile.commandline?.trim()\r\n ? profile.commandline\r\n : \"powershell.exe\";\r\n if (/(?:^|\\s)-NoLogo(?:\\s|$)/i.test(commandline)) continue;\r\n\r\n content = setSetting(\r\n content,\r\n [\"profiles\", \"list\", profile.index, \"commandline\"],\r\n `${commandline} -NoLogo`,\r\n );\r\n }\r\n }\r\n\r\n if (terminalIconsEnabled) {\r\n const defaultProfileIndex = getDefaultProfileIndex(content);\r\n content = setSetting(\r\n content,\r\n [\"profiles\", \"defaults\", \"font\", \"face\"],\r\n NERD_FONT_FAMILY,\r\n );\r\n if (defaultProfileIndex !== undefined) {\r\n content = setSetting(\r\n content,\r\n [\"profiles\", \"list\", defaultProfileIndex, \"font\", \"face\"],\r\n NERD_FONT_FAMILY,\r\n );\r\n }\r\n }\r\n\r\n if (terminalIconsEnabled) {\r\n await installNerdFont();\r\n installTerminalIconsModule();\r\n }\r\n\r\n const dirty = content !== originalContent;\r\n if (dirty) {\r\n const backupPath = createSettingsBackup(settingsPath);\r\n log.info(pc.dim(`Backup created at ${backupPath}`));\r\n writeSettingsFile(settingsPath, content);\r\n }\r\n\r\n if (terminalIconsEnabled) {\r\n addTerminalIconsToPowerShellProfile();\r\n }\r\n}\r\n\r\nexport async function runInstaller(): Promise<void> {\r\n console.log(pc.cyan(BANNER));\r\n intro(pc.bold(\"Pimp up your Terminal.\"));\r\n\r\n const selectableSettings = settings.filter(\r\n (setting) =>\r\n (setting.group === \"Appearance\" &&\r\n (setting.jsonPath !== undefined ||\r\n setting.id === \"terminalIcons\" ||\r\n setting.id === \"hidePowerShellBanner\")) ||\r\n (setting.group === \"Features\" &&\r\n (setting.jsonPath !== undefined ||\r\n setting.id === \"historyPreview\" ||\r\n setting.id === \"treeListing\")),\r\n );\r\n const settingsPath = findSettingsPath();\r\n const backups = settingsPath ? listSettingsBackups(settingsPath) : [];\r\n const answers = readConfiguredAnswers(settingsPath);\r\n let initialPickerValue = selectableSettings[0]?.id;\r\n let initialArea = \"Appearance\";\r\n\r\n while (true) {\r\n const areaOptions = [\r\n { value: \"Appearance\", label: \"Appearance\", hint: \"Colors and profile settings\" },\r\n { value: \"Features\", label: \"Features\", hint: \"Optional extras\" },\r\n { value: \"Other\", label: \"Other\", hint: \"Backups and recovery\" },\r\n ];\r\n if (Object.keys(answers).length > 0) {\r\n areaOptions.push({\r\n value: \"done\",\r\n label: \"Done\",\r\n hint: \"Review and apply your settings\",\r\n });\r\n }\r\n\r\n const selectedArea = bail(\r\n await select<string>({\r\n message: \"Choose an area\",\r\n options: areaOptions,\r\n initialValue: initialArea,\r\n }),\r\n );\r\n if (selectedArea === \"done\") break;\r\n\r\n initialArea = selectedArea;\r\n if (selectedArea === \"Other\") {\r\n if (backups.length === 0) {\r\n note(\r\n \"No backups yet. pimpt creates one before changing settings.json.\",\r\n \"Other\",\r\n );\r\n continue;\r\n }\r\n\r\n const selectedAction = bail(\r\n await select<string>({\r\n message: \"Other\",\r\n options: [\r\n {\r\n value: \"restoreBackup\",\r\n label: \"Restore settings backup\",\r\n hint: \"Choose a saved version\",\r\n },\r\n { value: \"back\", label: \"Back\", hint: \"Choose another area\" },\r\n ],\r\n initialValue: \"restoreBackup\",\r\n }),\r\n );\r\n if (selectedAction === \"back\") continue;\r\n if (!settingsPath) {\r\n throw new Error(\"Windows Terminal settings.json could not be found.\");\r\n }\r\n\r\n const selectedBackup = bail(\r\n await select<string>({\r\n message: \"Which backup should be restored?\",\r\n options: backups.map((backup) => ({\r\n value: backup.path,\r\n label: backup.createdAt.toLocaleString(),\r\n hint: backup.path,\r\n })),\r\n ...(backups[0] ? { initialValue: backups[0].path } : {}),\r\n }),\r\n );\r\n const shouldRestore = bail(\r\n await confirm({\r\n message:\r\n \"This replaces settings.json. The current file will be backed up first. Continue?\",\r\n initialValue: false,\r\n }),\r\n );\r\n if (!shouldRestore) continue;\r\n\r\n const restoreSpinner = spinner();\r\n restoreSpinner.start(\"Restoring settings.json backup…\");\r\n try {\r\n const safetyBackupPath = restoreSettingsBackup(\r\n settingsPath,\r\n selectedBackup,\r\n );\r\n restoreSpinner.stop(\"Settings restored successfully.\");\r\n log.info(\r\n pc.dim(`The previous settings were backed up to ${safetyBackupPath}`),\r\n );\r\n outro(pc.green(\"✓ Windows Terminal settings.json was restored.\"));\r\n } catch (error) {\r\n restoreSpinner.error(\"Could not restore the settings backup.\");\r\n throw error;\r\n }\r\n return;\r\n }\r\n\r\n while (true) {\r\n const visibleSettings = selectableSettings.filter(\r\n (setting) =>\r\n setting.group === selectedArea &&\r\n !(answers.terminalIcons === true && setting.id === \"fontFace\"),\r\n );\r\n const options = visibleSettings.map((setting) => ({\r\n value: setting.id,\r\n label:\r\n answers[setting.id] === undefined\r\n ? setting.label\r\n : `${pc.green(\"●\")} ${setting.label}`,\r\n hint: setting.hint,\r\n }));\r\n options.push({\r\n value: \"back\",\r\n label: \"Back\",\r\n hint: \"Choose another area\",\r\n });\r\n\r\n const firstOption = options[0];\r\n if (!firstOption) {\r\n throw new Error(`No settings are available in ${selectedArea}.`);\r\n }\r\n\r\n const selectedInitialValue =\r\n initialPickerValue &&\r\n options.some((option) => option.value === initialPickerValue)\r\n ? initialPickerValue\r\n : firstOption.value;\r\n const selectedId = bail(\r\n await select<string>({\r\n message: selectedArea,\r\n options,\r\n initialValue: selectedInitialValue,\r\n }),\r\n );\r\n if (selectedId === \"back\") break;\r\n\r\n const setting = selectableSettings.find(\r\n (candidate) =>\r\n candidate.id === selectedId && candidate.group === selectedArea,\r\n );\r\n if (!setting) {\r\n throw new Error(\r\n `Unknown setting selected in ${selectedArea}: ${selectedId}`,\r\n );\r\n }\r\n\r\n initialPickerValue = selectedId;\r\n log.step(pc.bold(pc.cyan(setting.group)));\r\n answers[setting.id] = await askSetting(setting, answers[setting.id]);\r\n if (setting.id === \"terminalIcons\" && answers.terminalIcons === true) {\r\n answers.fontFace = NERD_FONT_FAMILY;\r\n initialPickerValue = \"terminalIcons\";\r\n }\r\n }\r\n }\r\n\r\n renderSummary(answers);\r\n\r\n const proceed = bail(\r\n await confirm({\r\n message: \"Install these settings? (writes to settings.json)\",\r\n initialValue: true,\r\n }),\r\n );\r\n\r\n if (!proceed) {\r\n cancel(\"Setup cancelled. Nothing was changed.\");\r\n return;\r\n }\r\n\r\n const s = spinner();\r\n s.start(\"Building your configuration…\");\r\n await delay(300);\r\n s.message(\"Checking compatibility…\");\r\n await delay(300);\r\n s.message(\r\n answers.terminalIcons === true ||\r\n answers.historyPreview === true ||\r\n answers.treeListing === true ||\r\n answers.hidePowerShellBanner === true\r\n ? \"Applying PowerShell options…\"\r\n : \"Writing settings.json…\",\r\n );\r\n await delay(400);\r\n\r\n try {\r\n await applySettings(answers, settingsPath);\r\n if (answers.historyPreview === true) {\r\n installPSReadLineModule();\r\n addHistoryPreviewToPowerShellProfile();\r\n }\r\n if (answers.treeListing === true) {\r\n addTreeListingToPowerShellProfile();\r\n }\r\n } catch (error) {\r\n if (!(error instanceof InvalidSettingsFileError)) throw error;\r\n\r\n s.error(error.message);\r\n process.exitCode = 1;\r\n return;\r\n }\r\n\r\n s.stop(\"Configuration applied successfully.\");\r\n\r\n const fontSelected =\r\n answers.fontFace !== undefined && answers.fontFace !== \"keep\";\r\n const powerShellFeatureSelected =\r\n answers.terminalIcons === true ||\r\n answers.historyPreview === true ||\r\n answers.treeListing === true ||\r\n answers.hidePowerShellBanner === true;\r\n if (fontSelected || powerShellFeatureSelected) openNewTerminalTab();\r\n outro(\r\n [\r\n `${pc.green(\"✓\")} Your configuration is ready.`,\r\n pc.dim(\"Your selected settings and features are ready.\"),\r\n ].join(\"\\n\"),\r\n );\r\n}\r\n","export type SettingValue = string | boolean;\r\n\r\nexport type SettingGroup =\r\n | \"Appearance\"\r\n | \"Colors\"\r\n | \"Window & tabs\"\r\n | \"Profile\"\r\n | \"Behavior\"\r\n | \"Features\"\r\n | \"Other\";\r\n\r\nexport interface Choice {\r\n value: string;\r\n label: string;\r\n hint: string;\r\n}\r\n\r\nexport type Prompt =\r\n | {\r\n kind: \"select\";\r\n message: string;\r\n options: Choice[];\r\n initialValue: string;\r\n }\r\n | {\r\n kind: \"text\";\r\n message: string;\r\n placeholder: string;\r\n initialValue: string;\r\n validate?: (value: string | undefined) => string | undefined;\r\n }\r\n | {\r\n kind: \"confirm\";\r\n message: string;\r\n initialValue: boolean;\r\n };\r\n\r\nexport interface SettingDefinition {\r\n id: string;\r\n group: SettingGroup;\r\n label: string;\r\n hint: string;\r\n prompt: Prompt;\r\n summarize: (value: SettingValue) => string;\r\n /**\r\n * Pfad in der settings.json, an dem der Wert gespeichert wird.\r\n * z. B. [\"profiles\", \"defaults\", \"background\"]\r\n * Wenn undefined, wird das Setting nicht geschrieben.\r\n */\r\n jsonPath?: string[];\r\n /**\r\n * Wenn true, wird der Wert nur geschrieben, wenn er nicht \"keep\" ist.\r\n * Nutzt für Presets mit \"keep\"-Option.\r\n */\r\n skipIfKeep?: boolean;\r\n}\r\n\r\nexport const BACKGROUND_CUSTOM = \"custom\";\r\n\r\nconst transparencyOptions: Choice[] = [\r\n { value: \"off\", label: \"Off\", hint: \"Solid background\" },\r\n { value: \"90\", label: \"Subtle\", hint: \"90% opacity\" },\r\n { value: \"80\", label: \"Balanced\", hint: \"80% opacity\" },\r\n { value: \"70\", label: \"Frosted\", hint: \"70% opacity\" },\r\n { value: \"50\", label: \"Heavy\", hint: \"50% opacity\" },\r\n { value: \"0\", label: \"Fully transparent\", hint: \"Content 0%; tab row 50% acrylic\" },\r\n];\r\n\r\nconst backgroundOptions: Choice[] = [\r\n { value: \"keep\", label: \"Keep current\", hint: \"Leave the background unchanged\" },\r\n { value: \"#0B1021\", label: \"Midnight\", hint: \"#0B1021\" },\r\n { value: \"#2E3440\", label: \"Nord\", hint: \"#2E3440\" },\r\n { value: \"#282A36\", label: \"Dracula\", hint: \"#282A36\" },\r\n { value: \"#002B36\", label: \"Solarized Dark\", hint: \"#002B36\" },\r\n {\r\n value: BACKGROUND_CUSTOM,\r\n label: \"Custom hex\",\r\n hint: \"Enter your own color\",\r\n },\r\n];\r\n\r\nconst fontOptions: Choice[] = [\r\n { value: \"keep\", label: \"Keep current\", hint: \"Use the configured font\" },\r\n { value: \"Cascadia Mono\", label: \"Cascadia Mono\", hint: \"Windows Terminal default\" },\r\n { value: \"Cascadia Code\", label: \"Cascadia Code\", hint: \"Ligatures included\" },\r\n { value: \"Consolas\", label: \"Consolas\", hint: \"Classic Windows font\" },\r\n { value: \"JetBrains Mono\", label: \"JetBrains Mono\", hint: \"Popular developer font\" },\r\n { value: \"Fira Code\", label: \"Fira Code\", hint: \"Monospace with ligatures\" },\r\n { value: \"Hack\", label: \"Hack\", hint: \"Designed for source code\" },\r\n { value: \"Source Code Pro\", label: \"Source Code Pro\", hint: \"Adobe's monospace font\" },\r\n { value: \"IBM Plex Mono\", label: \"IBM Plex Mono\", hint: \"Technical, readable monospace\" },\r\n];\r\n\r\nconst fontSizeOptions: Choice[] = [\"10\", \"11\", \"12\", \"14\", \"16\", \"18\"].map(\r\n (value) => ({ value, label: `${value} pt`, hint: \"Points\" }),\r\n);\r\n\r\nconst cursorOptions: Choice[] = [\r\n { value: \"keep\", label: \"Keep current\", hint: \"Use the configured cursor\" },\r\n { value: \"bar\", label: \"Bar\", hint: \"Thin vertical line\" },\r\n { value: \"filledBox\", label: \"Block\", hint: \"Filled rectangle\" },\r\n { value: \"underscore\", label: \"Underline\", hint: \"Line below the text\" },\r\n { value: \"vintage\", label: \"Vintage\", hint: \"Retro terminal blink\" },\r\n];\r\n\r\nconst schemeOptions: Choice[] = [\r\n { value: \"keep\", label: \"Keep current\", hint: \"Use the configured scheme\" },\r\n { value: \"Campbell\", label: \"Campbell\", hint: \"Windows Terminal default\" },\r\n { value: \"One Half Dark\", label: \"One Half Dark\", hint: \"Cool, muted palette\" },\r\n { value: \"Solarized Dark\", label: \"Solarized Dark\", hint: \"Low-contrast classic\" },\r\n { value: \"Tango Dark\", label: \"Tango Dark\", hint: \"Colorful and warm\" },\r\n { value: \"Vintage\", label: \"Vintage\", hint: \"Retro phosphor look\" },\r\n];\r\n\r\nconst launchModeOptions: Choice[] = [\r\n { value: \"default\", label: \"Windowed\", hint: \"Normal window\" },\r\n { value: \"maximized\", label: \"Maximized\", hint: \"Fill the screen\" },\r\n { value: \"fullscreen\", label: \"Fullscreen\", hint: \"Hide the window frame\" },\r\n { value: \"focus\", label: \"Focus mode\", hint: \"Minimal distractions\" },\r\n {\r\n value: \"maximizedFocus\",\r\n label: \"Maximized focus\",\r\n hint: \"Maximized and distraction-free\",\r\n },\r\n];\r\n\r\nconst appThemeOptions: Choice[] = [\r\n { value: \"system\", label: \"System\", hint: \"Follow Windows\" },\r\n { value: \"dark\", label: \"Dark\", hint: \"Always dark\" },\r\n { value: \"light\", label: \"Light\", hint: \"Always light\" },\r\n];\r\n\r\nconst tabLayoutOptions: Choice[] = [\r\n { value: \"titlebar\", label: \"Tabs in titlebar\", hint: \"Compact, modern layout\" },\r\n { value: \"separate\", label: \"Separate tab row\", hint: \"Tabs below the titlebar\" },\r\n];\r\n\r\nconst tabWidthOptions: Choice[] = [\r\n { value: \"equal\", label: \"Equal\", hint: \"All tabs share the width\" },\r\n { value: \"titleLength\", label: \"Title length\", hint: \"Width fits the title\" },\r\n { value: \"compact\", label: \"Compact\", hint: \"Shrink to fit\" },\r\n];\r\n\r\nconst iconOptions: Choice[] = [\r\n { value: \"classic\", label: \"Classic terminal\", hint: \"Monochrome prompt glyph\" },\r\n { value: \"rocket\", label: \"Rocket\", hint: \"Launch-ready\" },\r\n { value: \"bolt\", label: \"Bolt\", hint: \"Fast and loud\" },\r\n { value: \"code\", label: \"Code\", hint: \"Developer vibes\" },\r\n];\r\n\r\nfunction labelOf(options: Choice[], value: string): string {\r\n return options.find((option) => option.value === value)?.label ?? value;\r\n}\r\n\r\nfunction onOff(value: SettingValue): string {\r\n return value === true ? \"Enabled\" : \"Disabled\";\r\n}\r\n\r\nexport const settings: SettingDefinition[] = [\r\n {\r\n id: \"transparency\",\r\n group: \"Appearance\",\r\n label: \"Transparency\",\r\n hint: \"Window opacity\",\r\n prompt: {\r\n kind: \"select\",\r\n message: \"How transparent should the window be?\",\r\n options: transparencyOptions,\r\n initialValue: \"80\",\r\n },\r\n summarize: (value) => {\r\n if (value === \"off\") return \"Off\";\r\n if (value === \"0\") return \"Fully transparent content\";\r\n return `Acrylic · ${String(value)}% opacity`;\r\n },\r\n jsonPath: [\"profiles\", \"defaults\", \"opacity\"],\r\n },\r\n {\r\n id: \"background\",\r\n group: \"Appearance\",\r\n label: \"Background color\",\r\n hint: \"Preset or custom color\",\r\n prompt: {\r\n kind: \"select\",\r\n message: \"Pick a background color\",\r\n options: backgroundOptions,\r\n initialValue: \"keep\",\r\n },\r\n summarize: (value) => {\r\n if (value === \"keep\") return \"Keep current\";\r\n const preset = backgroundOptions.find(\r\n (option) => option.value === value && option.value !== \"keep\" && option.value !== BACKGROUND_CUSTOM,\r\n );\r\n return preset ? `${preset.label} (${preset.value})` : `Custom (${String(value)})`;\r\n },\r\n jsonPath: [\"profiles\", \"defaults\", \"background\"],\r\n skipIfKeep: true,\r\n },\r\n {\r\n id: \"backgroundImage\",\r\n group: \"Appearance\",\r\n label: \"Background image\",\r\n hint: \"Path to a local image\",\r\n prompt: {\r\n kind: \"text\",\r\n message: \"Path to a background image (leave empty to skip)\",\r\n placeholder: \"C:\\\\Users\\\\you\\\\wallpaper.png\",\r\n initialValue: \"\",\r\n },\r\n summarize: (value) => (String(value).trim() ? String(value) : \"Not set\"),\r\n },\r\n {\r\n id: \"fontFace\",\r\n group: \"Appearance\",\r\n label: \"Font\",\r\n hint: \"Terminal font\",\r\n prompt: {\r\n kind: \"select\",\r\n message: \"Choose a font\",\r\n options: fontOptions,\r\n initialValue: \"keep\",\r\n },\r\n summarize: (value) => labelOf(fontOptions, String(value)),\r\n jsonPath: [\"profiles\", \"defaults\", \"font\", \"face\"],\r\n skipIfKeep: true,\r\n },\r\n {\r\n id: \"fontSize\",\r\n group: \"Appearance\",\r\n label: \"Font size\",\r\n hint: \"Text size in points\",\r\n prompt: {\r\n kind: \"select\",\r\n message: \"Choose a font size\",\r\n options: fontSizeOptions,\r\n initialValue: \"12\",\r\n },\r\n summarize: (value) => `${String(value)} pt`,\r\n },\r\n {\r\n id: \"cursorShape\",\r\n group: \"Appearance\",\r\n label: \"Cursor\",\r\n hint: \"Shape of the text cursor\",\r\n prompt: {\r\n kind: \"select\",\r\n message: \"Choose a cursor shape\",\r\n options: cursorOptions,\r\n initialValue: \"keep\",\r\n },\r\n summarize: (value) => labelOf(cursorOptions, String(value)),\r\n },\r\n {\r\n id: \"colorScheme\",\r\n group: \"Colors\",\r\n label: \"Color scheme\",\r\n hint: \"ANSI palette for text and accents\",\r\n prompt: {\r\n kind: \"select\",\r\n message: \"Choose a color scheme\",\r\n options: schemeOptions,\r\n initialValue: \"keep\",\r\n },\r\n summarize: (value) => labelOf(schemeOptions, String(value)),\r\n },\r\n {\r\n id: \"launchMode\",\r\n group: \"Window & tabs\",\r\n label: \"Launch mode\",\r\n hint: \"How the window opens\",\r\n prompt: {\r\n kind: \"select\",\r\n message: \"How should Windows Terminal open?\",\r\n options: launchModeOptions,\r\n initialValue: \"default\",\r\n },\r\n summarize: (value) => labelOf(launchModeOptions, String(value)),\r\n },\r\n {\r\n id: \"appTheme\",\r\n group: \"Window & tabs\",\r\n label: \"Application theme\",\r\n hint: \"Light, dark, or follow Windows\",\r\n prompt: {\r\n kind: \"select\",\r\n message: \"Choose the application theme\",\r\n options: appThemeOptions,\r\n initialValue: \"system\",\r\n },\r\n summarize: (value) => labelOf(appThemeOptions, String(value)),\r\n },\r\n {\r\n id: \"tabLayout\",\r\n group: \"Window & tabs\",\r\n label: \"Tab bar\",\r\n hint: \"Where the tab row is displayed\",\r\n prompt: {\r\n kind: \"select\",\r\n message: \"Where should the tab bar live?\",\r\n options: tabLayoutOptions,\r\n initialValue: \"titlebar\",\r\n },\r\n summarize: (value) => labelOf(tabLayoutOptions, String(value)),\r\n },\r\n {\r\n id: \"tabWidthMode\",\r\n group: \"Window & tabs\",\r\n label: \"Tab width\",\r\n hint: \"How tab widths are calculated\",\r\n prompt: {\r\n kind: \"select\",\r\n message: \"How should tabs be sized?\",\r\n options: tabWidthOptions,\r\n initialValue: \"equal\",\r\n },\r\n summarize: (value) => labelOf(tabWidthOptions, String(value)),\r\n },\r\n {\r\n id: \"icon\",\r\n group: \"Profile\",\r\n label: \"Profile icon\",\r\n hint: \"Icon style for your profile\",\r\n prompt: {\r\n kind: \"select\",\r\n message: \"Pick a profile icon style\",\r\n options: iconOptions,\r\n initialValue: \"classic\",\r\n },\r\n summarize: (value) => labelOf(iconOptions, String(value)),\r\n },\r\n {\r\n id: \"tabTitle\",\r\n group: \"Profile\",\r\n label: \"Tab title\",\r\n hint: \"Custom title shown on the tab\",\r\n prompt: {\r\n kind: \"text\",\r\n message: \"Custom tab title (leave empty for automatic)\",\r\n placeholder: \"pimpt\",\r\n initialValue: \"\",\r\n },\r\n summarize: (value) => (String(value).trim() ? String(value) : \"Automatic\"),\r\n },\r\n {\r\n id: \"startingDirectory\",\r\n group: \"Features\",\r\n label: \"Starting directory\",\r\n hint: \"Default shell folder\",\r\n prompt: {\r\n kind: \"text\",\r\n message: \"Enter or paste a path; relative paths start in your user folder\",\r\n placeholder: \"C:\\\\Users\\\\you\\\\Projects\",\r\n initialValue: \"\",\r\n },\r\n summarize: (value) => (String(value).trim() ? String(value) : \"Default\"),\r\n jsonPath: [\"profiles\", \"defaults\", \"startingDirectory\"],\r\n },\r\n {\r\n id: \"copyOnSelect\",\r\n group: \"Behavior\",\r\n label: \"Copy on select\",\r\n hint: \"Copy text as soon as it is selected\",\r\n prompt: {\r\n kind: \"confirm\",\r\n message: \"Copy text automatically when selected?\",\r\n initialValue: false,\r\n },\r\n summarize: onOff,\r\n },\r\n {\r\n id: \"confirmClose\",\r\n group: \"Behavior\",\r\n label: \"Confirm close\",\r\n hint: \"Ask before closing multiple tabs\",\r\n prompt: {\r\n kind: \"confirm\",\r\n message: \"Confirm before closing a window with many tabs?\",\r\n initialValue: true,\r\n },\r\n summarize: onOff,\r\n },\r\n {\r\n id: \"terminalIcons\",\r\n group: \"Appearance\",\r\n label: \"PowerShell file icons\",\r\n hint: \"File icons in PowerShell\",\r\n prompt: {\r\n kind: \"confirm\",\r\n message:\r\n \"Enable PowerShell file icons? This installs Terminal-Icons and Hack Nerd Font Mono if needed, adds it to your PowerShell profile, and switches Windows Terminal to that font.\",\r\n initialValue: true,\r\n },\r\n summarize: onOff,\r\n },\r\n {\r\n id: \"historyPreview\",\r\n group: \"Features\",\r\n label: \"Command history preview\",\r\n hint: \"Browse recent commands\",\r\n prompt: {\r\n kind: \"confirm\",\r\n message:\r\n \"Enable a scrollable PowerShell history list? This installs PSReadLine if needed and lets the Up and Down arrows browse the visible history suggestions.\",\r\n initialValue: true,\r\n },\r\n summarize: onOff,\r\n },\r\n {\r\n id: \"treeListing\",\r\n group: \"Features\",\r\n label: \"Tree-style ls\",\r\n hint: \"Show files in a colored directory tree\",\r\n prompt: {\r\n kind: \"confirm\",\r\n message:\r\n \"Show directory contents as a colored tree when you run ls? Output is capped at 50 entries by default. Use -Limit or -All for more. Get-ChildItem remains available as gci.\",\r\n initialValue: true,\r\n },\r\n summarize: onOff,\r\n },\r\n {\r\n id: \"hidePowerShellBanner\",\r\n group: \"Appearance\",\r\n label: \"Hide PowerShell startup banner\",\r\n hint: \"Hide the welcome text\",\r\n prompt: {\r\n kind: \"confirm\",\r\n message: \"Hide the Windows PowerShell startup banner?\",\r\n initialValue: true,\r\n },\r\n summarize: onOff,\r\n },\r\n {\r\n id: \"focusFollowMouse\",\r\n group: \"Behavior\",\r\n label: \"Focus follows mouse\",\r\n hint: \"Focus panes on hover\",\r\n prompt: {\r\n kind: \"confirm\",\r\n message: \"Focus panes when hovering with the mouse?\",\r\n initialValue: false,\r\n },\r\n summarize: onOff,\r\n },\r\n {\r\n id: \"trimPaste\",\r\n group: \"Behavior\",\r\n label: \"Trim paste\",\r\n hint: \"Remove trailing whitespace when pasting\",\r\n prompt: {\r\n kind: \"confirm\",\r\n message: \"Trim trailing whitespace when pasting?\",\r\n initialValue: true,\r\n },\r\n summarize: onOff,\r\n },\r\n];\r\n\r\nexport const groupOrder: SettingGroup[] = [\r\n \"Appearance\",\r\n \"Colors\",\r\n \"Window & tabs\",\r\n \"Profile\",\r\n \"Behavior\",\r\n \"Features\",\r\n \"Other\",\r\n];\r\n\r\nexport function buildGroupedOptions(): Record<string, Choice[]> {\r\n const grouped: Record<string, Choice[]> = {};\r\n\r\n for (const group of groupOrder) {\r\n grouped[group] = settings\r\n .filter((setting) => setting.group === group)\r\n .map((setting) => ({\r\n value: setting.id,\r\n label: setting.label,\r\n hint: setting.hint,\r\n }));\r\n }\r\n\r\n return grouped;\r\n}\r\n","import { createHash } from \"node:crypto\";\r\nimport { execFileSync, spawnSync } from \"node:child_process\";\r\nimport { mkdir, mkdtemp, rm, writeFile } from \"node:fs/promises\";\r\nimport { tmpdir } from \"node:os\";\r\nimport { join, resolve } from \"node:path\";\r\n\r\ninterface FontAsset {\r\n fileName: string;\r\n fontUrl: string;\r\n licenseFileName: string;\r\n licenseUrl: string;\r\n}\r\n\r\nconst googleFontsRevision = \"29b4ec6df2522a8aee279414b78a07910b065874\";\r\nconst hackRevision = \"a737c121cabb337fdfe655d8c7304729f351e30f\";\r\nconst fontRegistryKeys = [\r\n \"HKLM\\\\SOFTWARE\\\\Microsoft\\\\Windows NT\\\\CurrentVersion\\\\Fonts\",\r\n \"HKCU\\\\SOFTWARE\\\\Microsoft\\\\Windows NT\\\\CurrentVersion\\\\Fonts\",\r\n];\r\nconst userFontsRegistryKey =\r\n \"HKCU\\\\SOFTWARE\\\\Microsoft\\\\Windows NT\\\\CurrentVersion\\\\Fonts\";\r\nexport const NERD_FONT_FAMILY = \"Hack Nerd Font Mono\";\r\nconst nerdFontArchive = {\r\n fileName: \"Hack.tar.xz\",\r\n url: \"https://github.com/ryanoasis/nerd-fonts/releases/download/v3.5.1/Hack.tar.xz\",\r\n sha256: \"cdd389472e10e2261520140ff1b382b4f8a226af5fd0b2735b975d31151d9c3c\",\r\n fontEntry: \"HackNerdFontMono-Regular.ttf\",\r\n licenseEntry: \"LICENSE.md\",\r\n};\r\n\r\nconst fontAssets: Record<string, FontAsset> = {\r\n \"Cascadia Mono\": {\r\n fileName: `pimpt-cascadia-mono-${googleFontsRevision.slice(0, 8)}.ttf`,\r\n fontUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/cascadiamono/CascadiaMono%5Bwght%5D.ttf`,\r\n licenseFileName: \"pimpt-cascadia-mono-OFL.txt\",\r\n licenseUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/cascadiamono/OFL.txt`,\r\n },\r\n \"Cascadia Code\": {\r\n fileName: `pimpt-cascadia-code-${googleFontsRevision.slice(0, 8)}.ttf`,\r\n fontUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/cascadiacode/CascadiaCode%5Bwght%5D.ttf`,\r\n licenseFileName: \"pimpt-cascadia-code-OFL.txt\",\r\n licenseUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/cascadiacode/OFL.txt`,\r\n },\r\n \"JetBrains Mono\": {\r\n fileName: `pimpt-jetbrains-mono-${googleFontsRevision.slice(0, 8)}.ttf`,\r\n fontUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/jetbrainsmono/JetBrainsMono%5Bwght%5D.ttf`,\r\n licenseFileName: \"pimpt-jetbrains-mono-OFL.txt\",\r\n licenseUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/jetbrainsmono/OFL.txt`,\r\n },\r\n \"Fira Code\": {\r\n fileName: `pimpt-fira-code-${googleFontsRevision.slice(0, 8)}.ttf`,\r\n fontUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/firacode/FiraCode%5Bwght%5D.ttf`,\r\n licenseFileName: \"pimpt-fira-code-OFL.txt\",\r\n licenseUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/firacode/OFL.txt`,\r\n },\r\n Hack: {\r\n fileName: `pimpt-hack-${hackRevision.slice(0, 8)}.ttf`,\r\n fontUrl: `https://raw.githubusercontent.com/source-foundry/Hack/${hackRevision}/build/ttf/Hack-Regular.ttf`,\r\n licenseFileName: \"pimpt-hack-LICENSE.md\",\r\n licenseUrl: `https://raw.githubusercontent.com/source-foundry/Hack/${hackRevision}/LICENSE.md`,\r\n },\r\n \"Source Code Pro\": {\r\n fileName: `pimpt-source-code-pro-${googleFontsRevision.slice(0, 8)}.ttf`,\r\n fontUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/sourcecodepro/SourceCodePro%5Bwght%5D.ttf`,\r\n licenseFileName: \"pimpt-source-code-pro-OFL.txt\",\r\n licenseUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/sourcecodepro/OFL.txt`,\r\n },\r\n \"IBM Plex Mono\": {\r\n fileName: `pimpt-ibm-plex-mono-${googleFontsRevision.slice(0, 8)}.ttf`,\r\n fontUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/ibmplexmono/IBMPlexMono-Regular.ttf`,\r\n licenseFileName: \"pimpt-ibm-plex-mono-OFL.txt\",\r\n licenseUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/ibmplexmono/OFL.txt`,\r\n },\r\n};\r\n\r\nfunction assertWindows(): void {\r\n if (process.platform !== \"win32\") {\r\n throw new Error(\"Automatic font installation is only available on Windows.\");\r\n }\r\n}\r\n\r\nfunction queryFontRegistry(key: string): string {\r\n const result = spawnSync(\"reg.exe\", [\"query\", key], {\r\n encoding: \"utf8\",\r\n windowsHide: true,\r\n });\r\n if (result.error) {\r\n throw new Error(`Could not query the Windows font registry: ${result.error.message}`, {\r\n cause: result.error,\r\n });\r\n }\r\n if (result.status === 1) return \"\";\r\n if (result.status !== 0) {\r\n throw new Error(\r\n `Could not query the Windows font registry: ${result.stderr.trim() || `reg.exe exited with code ${String(result.status)}`}`,\r\n );\r\n }\r\n return result.stdout;\r\n}\r\n\r\nexport function isFontInstalled(fontFamily: string): boolean {\r\n assertWindows();\r\n const family = fontFamily.toLocaleLowerCase(\"en-US\");\r\n return fontRegistryKeys\r\n .map(queryFontRegistry)\r\n .join(\"\\n\")\r\n .split(/\\r?\\n/)\r\n .some((line) => line.trimStart().toLocaleLowerCase(\"en-US\").startsWith(family));\r\n}\r\n\r\nexport function canInstallFont(fontFamily: string): boolean {\r\n return fontAssets[fontFamily] !== undefined;\r\n}\r\n\r\nasync function download(url: string, description: string): Promise<Buffer> {\r\n let response: Response;\r\n try {\r\n response = await fetch(url, { signal: AbortSignal.timeout(30_000) });\r\n } catch (error) {\r\n throw new Error(`Could not download ${description}: ${String(error)}`, {\r\n cause: error,\r\n });\r\n }\r\n\r\n if (!response.ok) {\r\n throw new Error(`Could not download ${description}: HTTP ${response.status}.`);\r\n }\r\n\r\n const data = Buffer.from(await response.arrayBuffer());\r\n if (data.length === 0 || data.length > 30_000_000) {\r\n throw new Error(`Downloaded ${description} has an invalid file size.`);\r\n }\r\n return data;\r\n}\r\n\r\nfunction isFontFile(data: Buffer): boolean {\r\n return (\r\n (data[0] === 0 && data[1] === 1 && data[2] === 0 && data[3] === 0) ||\r\n data.toString(\"ascii\", 0, 4) === \"OTTO\"\r\n );\r\n}\r\n\r\nasync function saveAndRegisterFont(\r\n localAppData: string,\r\n fontFamily: string,\r\n fileName: string,\r\n licenseFileName: string,\r\n fontData: Buffer,\r\n licenseData: Buffer,\r\n): Promise<void> {\r\n if (!isFontFile(fontData)) {\r\n throw new Error(\r\n `The downloaded ${fontFamily} file is not a valid TrueType/OpenType font.`,\r\n );\r\n }\r\n\r\n const licenseText = licenseData.toString(\"utf8\").toLowerCase();\r\n if (!licenseText.includes(\"license\")) {\r\n throw new Error(`The downloaded ${fontFamily} license file is invalid.`);\r\n }\r\n\r\n const fontDirectory = join(localAppData, \"Microsoft\", \"Windows\", \"Fonts\");\r\n await mkdir(fontDirectory, { recursive: true });\r\n\r\n const fontPath = join(fontDirectory, fileName);\r\n const licensePath = join(fontDirectory, licenseFileName);\r\n await writeFile(fontPath, fontData);\r\n await writeFile(licensePath, licenseData);\r\n\r\n execFileSync(\r\n \"reg.exe\",\r\n [\r\n \"add\",\r\n userFontsRegistryKey,\r\n \"/v\",\r\n `${fontFamily} (TrueType)`,\r\n \"/t\",\r\n \"REG_SZ\",\r\n \"/d\",\r\n fontPath,\r\n \"/f\",\r\n ],\r\n { encoding: \"utf8\", windowsHide: true, stdio: \"pipe\" },\r\n );\r\n}\r\n\r\nexport async function installFont(fontFamily: string): Promise<void> {\r\n assertWindows();\r\n const asset = fontAssets[fontFamily];\r\n if (!asset) {\r\n throw new Error(`Automatic installation is not supported for ${fontFamily}.`);\r\n }\r\n\r\n const localAppData = process.env.LOCALAPPDATA;\r\n if (!localAppData) {\r\n throw new Error(\"LOCALAPPDATA is not set; the font cannot be installed.\");\r\n }\r\n\r\n const [fontData, licenseData] = await Promise.all([\r\n download(asset.fontUrl, `${fontFamily} font`),\r\n download(asset.licenseUrl, `${fontFamily} license`),\r\n ]);\r\n await saveAndRegisterFont(\r\n localAppData,\r\n fontFamily,\r\n asset.fileName,\r\n asset.licenseFileName,\r\n fontData,\r\n licenseData,\r\n );\r\n}\r\n\r\nexport async function installNerdFont(): Promise<void> {\r\n assertWindows();\r\n if (isFontInstalled(NERD_FONT_FAMILY)) return;\r\n\r\n const localAppData = process.env.LOCALAPPDATA;\r\n if (!localAppData) {\r\n throw new Error(\"LOCALAPPDATA is not set; the font cannot be installed.\");\r\n }\r\n\r\n const archiveData = await download(nerdFontArchive.url, \"Hack Nerd Font archive\");\r\n const actualHash = createHash(\"sha256\").update(archiveData).digest(\"hex\");\r\n if (actualHash !== nerdFontArchive.sha256) {\r\n throw new Error(\"The downloaded Hack Nerd Font archive failed its SHA-256 check.\");\r\n }\r\n\r\n const temporaryDirectory = await mkdtemp(join(tmpdir(), \"pimpt-nerd-font-\"));\r\n const archivePath = resolve(temporaryDirectory, nerdFontArchive.fileName);\r\n try {\r\n await writeFile(archivePath, archiveData);\r\n let fontData: Buffer;\r\n let licenseData: Buffer;\r\n try {\r\n fontData = execFileSync(\r\n \"tar.exe\",\r\n [\"-xOf\", archivePath, nerdFontArchive.fontEntry],\r\n { maxBuffer: 10_000_000, windowsHide: true },\r\n );\r\n licenseData = execFileSync(\r\n \"tar.exe\",\r\n [\"-xOf\", archivePath, nerdFontArchive.licenseEntry],\r\n { maxBuffer: 1_000_000, windowsHide: true },\r\n );\r\n } catch (error) {\r\n throw new Error(\"Could not extract Hack Nerd Font from its archive.\", {\r\n cause: error,\r\n });\r\n }\r\n\r\n await saveAndRegisterFont(\r\n localAppData,\r\n NERD_FONT_FAMILY,\r\n \"pimpt-hack-nerd-font-v3.5.1.ttf\",\r\n \"pimpt-hack-nerd-font-LICENSE.md\",\r\n fontData,\r\n licenseData,\r\n );\r\n } finally {\r\n await rm(temporaryDirectory, { recursive: true, force: true });\r\n }\r\n}\r\n","import { execFileSync } from \"node:child_process\";\r\n\r\nconst terminalIconsVersion = \"0.11.0\";\r\nconst psReadLineVersion = \"2.4.5\";\r\n\r\nfunction runPowerShell(script: string, operation: string): void {\r\n if (process.platform !== \"win32\") {\r\n throw new Error(`${operation} is only supported on Windows.`);\r\n }\r\n\r\n try {\r\n execFileSync(\r\n \"powershell.exe\",\r\n [\r\n \"-NoLogo\",\r\n \"-NoProfile\",\r\n \"-NonInteractive\",\r\n \"-Command\",\r\n script,\r\n ],\r\n { encoding: \"utf8\", windowsHide: true, stdio: \"pipe\" },\r\n );\r\n } catch (error) {\r\n throw new Error(`${operation} failed: ${String(error)}`, { cause: error });\r\n }\r\n}\r\n\r\nfunction installPowerShellGalleryModule(\r\n moduleName: \"Terminal-Icons\" | \"PSReadLine\",\r\n version: string,\r\n allowClobber: boolean,\r\n): void {\r\n const clobberOption = allowClobber ? \"-AllowClobber \" : \"\";\r\n const script = String.raw`$ErrorActionPreference = 'Stop'\r\n$protocols = [Net.ServicePointManager]::SecurityProtocol -bor [Net.SecurityProtocolType]::Tls12\r\n[Net.ServicePointManager]::SecurityProtocol = $protocols\r\n$nugetProvider = Get-PackageProvider -Name NuGet -ListAvailable -ErrorAction SilentlyContinue\r\nif (-not $nugetProvider) {\r\n Install-PackageProvider -Name NuGet -MinimumVersion '2.8.5.201' -Scope CurrentUser -Force -Confirm:$false -ErrorAction Stop | Out-Null\r\n}\r\n\r\n$requiredVersion = [version]'${version}'\r\n$module = Get-Module -ListAvailable -Name '${moduleName}' | Where-Object { $_.Version -eq $requiredVersion }\r\nif (-not $module) {\r\n Install-Module -Name '${moduleName}' -RequiredVersion '${version}' -Scope CurrentUser -Repository PSGallery ${clobberOption}-Force -Confirm:$false -ErrorAction Stop\r\n}\r\n\r\n$module = Get-Module -ListAvailable -Name '${moduleName}' | Where-Object { $_.Version -eq $requiredVersion }\r\nif (-not $module) {\r\n throw '${moduleName} ${version} is not available after installation.'\r\n}`;\r\n runPowerShell(script, `Installing the ${moduleName} PowerShell module`);\r\n}\r\n\r\nfunction addPowerShellProfileBlock(\r\n feature:\r\n | \"terminal icons\"\r\n | \"command history preview\"\r\n | \"tree-style ls\"\r\n | \"tree-style ls alias\"\r\n | \"tree-style ls v2\",\r\n commands: string[],\r\n operation: string,\r\n): void {\r\n const beginMarker = `# >>> pimpt ${feature} >>>`;\r\n const endMarker = `# <<< pimpt ${feature} <<<`;\r\n const block = [beginMarker, ...commands, endMarker].join(\"\\r\\n\");\r\n const encodedMarker = Buffer.from(beginMarker, \"utf16le\").toString(\"base64\");\r\n const encodedBlock = Buffer.from(block, \"utf16le\").toString(\"base64\");\r\n const script = String.raw`$ErrorActionPreference = 'Stop'\r\n$profilePath = $PROFILE.CurrentUserCurrentHost\r\n$profileDirectory = Split-Path -Parent $profilePath\r\nif (-not (Test-Path -LiteralPath $profileDirectory)) {\r\n New-Item -ItemType Directory -Path $profileDirectory -Force | Out-Null\r\n}\r\n\r\n$profileContent = ''\r\nif (Test-Path -LiteralPath $profilePath) {\r\n $profileContent = Get-Content -LiteralPath $profilePath -Raw\r\n}\r\n\r\n$beginMarker = [System.Text.Encoding]::Unicode.GetString([Convert]::FromBase64String('${encodedMarker}'))\r\nif ($profileContent -notmatch [regex]::Escape($beginMarker)) {\r\n if (-not (Test-Path -LiteralPath $profilePath)) {\r\n New-Item -ItemType File -Path $profilePath -Force | Out-Null\r\n }\r\n\r\n $encoding = 'Default'\r\n $bytes = [System.IO.File]::ReadAllBytes($profilePath)\r\n if ($bytes.Length -ge 2 -and $bytes[0] -eq 0xFF -and $bytes[1] -eq 0xFE) {\r\n $encoding = 'Unicode'\r\n } elseif ($bytes.Length -ge 2 -and $bytes[0] -eq 0xFE -and $bytes[1] -eq 0xFF) {\r\n $encoding = 'BigEndianUnicode'\r\n } elseif ($bytes.Length -ge 3 -and $bytes[0] -eq 0xEF -and $bytes[1] -eq 0xBB -and $bytes[2] -eq 0xBF) {\r\n $encoding = 'UTF8'\r\n }\r\n\r\n $profileBlock = [System.Text.Encoding]::Unicode.GetString([Convert]::FromBase64String('${encodedBlock}'))\r\n $newline = [Environment]::NewLine\r\n $separator = if ($profileContent.Length -gt 0 -and -not $profileContent.EndsWith([string][char]10)) { $newline } else { '' }\r\n Add-Content -LiteralPath $profilePath -Encoding $encoding -Value \"$separator$profileBlock\"\r\n}`;\r\n runPowerShell(script, operation);\r\n}\r\n\r\nexport function installTerminalIconsModule(): void {\r\n installPowerShellGalleryModule(\r\n \"Terminal-Icons\",\r\n terminalIconsVersion,\r\n false,\r\n );\r\n}\r\n\r\nexport function installPSReadLineModule(): void {\r\n installPowerShellGalleryModule(\"PSReadLine\", psReadLineVersion, true);\r\n}\r\n\r\nexport function addTerminalIconsToPowerShellProfile(): void {\r\n addPowerShellProfileBlock(\r\n \"terminal icons\",\r\n [\"Import-Module Terminal-Icons -ErrorAction Stop\"],\r\n \"Adding Terminal-Icons to the Windows PowerShell profile\",\r\n );\r\n}\r\n\r\nexport function addHistoryPreviewToPowerShellProfile(): void {\r\n addPowerShellProfileBlock(\r\n \"command history preview\",\r\n [\r\n `Import-Module PSReadLine -RequiredVersion '${psReadLineVersion}' -Force -ErrorAction Stop`,\r\n \"Set-PSReadLineOption -PredictionSource History -PredictionViewStyle ListView\",\r\n ],\r\n \"Adding command history preview to the Windows PowerShell profile\",\r\n );\r\n}\r\n\r\nexport interface PowerShellProfileFeatures {\r\n terminalIcons: boolean;\r\n historyPreview: boolean;\r\n treeListing: boolean;\r\n}\r\n\r\nexport function readPowerShellProfileFeatures(): PowerShellProfileFeatures {\r\n const features: PowerShellProfileFeatures = {\r\n terminalIcons: false,\r\n historyPreview: false,\r\n treeListing: false,\r\n };\r\n if (process.platform !== \"win32\") return features;\r\n\r\n let encodedProfile: string;\r\n try {\r\n encodedProfile = execFileSync(\r\n \"powershell.exe\",\r\n [\r\n \"-NoLogo\",\r\n \"-NoProfile\",\r\n \"-NonInteractive\",\r\n \"-Command\",\r\n String.raw`$profilePath = $PROFILE.CurrentUserCurrentHost\r\nif (Test-Path -LiteralPath $profilePath) {\r\n $content = [System.IO.File]::ReadAllText($profilePath)\r\n [Console]::Out.Write([Convert]::ToBase64String([System.Text.Encoding]::Unicode.GetBytes($content)))\r\n}`,\r\n ],\r\n { encoding: \"utf8\", windowsHide: true, stdio: \"pipe\" },\r\n ).trim();\r\n } catch (error) {\r\n throw new Error(\"Could not inspect the Windows PowerShell profile.\", {\r\n cause: error,\r\n });\r\n }\r\n\r\n const profile = Buffer.from(encodedProfile, \"base64\").toString(\"utf16le\");\r\n const hasBlock = (name: string) =>\r\n profile.includes(`# >>> pimpt ${name} >>>`) &&\r\n profile.includes(`# <<< pimpt ${name} <<<`);\r\n\r\n features.terminalIcons = hasBlock(\"terminal icons\");\r\n features.historyPreview = hasBlock(\"command history preview\");\r\n features.treeListing =\r\n hasBlock(\"tree-style ls v2\") || hasBlock(\"tree-style ls\");\r\n return features;\r\n}\r\n\r\nexport function addTreeListingToPowerShellProfile(): void {\r\n addPowerShellProfileBlock(\r\n \"tree-style ls alias\",\r\n [\"Remove-Item Alias:ls -Force -ErrorAction SilentlyContinue\"],\r\n \"Enabling the tree-style ls command in the Windows PowerShell profile\",\r\n );\r\n addPowerShellProfileBlock(\r\n \"tree-style ls v2\",\r\n [\r\n \"function ls {\",\r\n \" [CmdletBinding()]\",\r\n \" param(\",\r\n \" [Parameter(Position = 0)] [string]$Path = '.',\",\r\n \" [ValidateRange(1, 32)] [int]$Depth = 4,\",\r\n \" [ValidateRange(1, 10000)] [int]$Limit = 50,\",\r\n \" [switch]$All,\",\r\n \" [switch]$Force\",\r\n \" )\",\r\n \" try {\",\r\n \" $root = Get-Item -LiteralPath $Path -ErrorAction Stop\",\r\n \" } catch {\",\r\n \" Write-Host (\\\"ls: cannot access '{0}': {1}\\\" -f $Path, $_.Exception.Message) -ForegroundColor Red\",\r\n \" return\",\r\n \" }\",\r\n \" if (-not $root.PSIsContainer) {\",\r\n \" Write-Host $root.Name -ForegroundColor Gray\",\r\n \" return\",\r\n \" }\",\r\n \" Write-Host $root.FullName -ForegroundColor Cyan\",\r\n \" $state = [pscustomobject]@{ Shown = 0; Limit = $Limit; All = [bool]$All; Truncated = $false }\",\r\n \" $walk = {\",\r\n \" param($Directory, [string]$Prefix, [int]$CurrentDepth, $State)\",\r\n \" if ($CurrentDepth -ge $Depth) { return }\",\r\n \" try {\",\r\n \" $children = @(Get-ChildItem -LiteralPath $Directory.FullName -Force:$Force -ErrorAction Stop | Sort-Object @{ Expression = { if ($_.PSIsContainer) { 0 } else { 1 } } }, Name)\",\r\n \" } catch {\",\r\n \" Write-Host (\\\"{0}└── [cannot read: {1}]\\\" -f $Prefix, $_.Exception.Message) -ForegroundColor Red\",\r\n \" return\",\r\n \" }\",\r\n \" for ($index = 0; $index -lt $children.Count; $index++) {\",\r\n \" if (-not $State.All -and $State.Shown -ge $State.Limit) {\",\r\n \" $State.Truncated = $true\",\r\n \" break\",\r\n \" }\",\r\n \" $entry = $children[$index]\",\r\n \" $isLast = $index -eq ($children.Count - 1)\",\r\n \" $connector = if ($isLast) { '└── ' } else { '├── ' }\",\r\n \" $color = if ($entry.PSIsContainer) { 'Cyan' } else { 'Gray' }\",\r\n \" Write-Host ($Prefix + $connector + $entry.Name) -ForegroundColor $color\",\r\n \" $State.Shown++\",\r\n \" if ($entry.PSIsContainer -and ($CurrentDepth + 1 -lt $Depth)) {\",\r\n \" $childPrefix = $Prefix + $(if ($isLast) { ' ' } else { '│ ' })\",\r\n \" & $walk $entry $childPrefix ($CurrentDepth + 1) $State\",\r\n \" if ($State.Truncated) { break }\",\r\n \" }\",\r\n \" }\",\r\n \" }\",\r\n \" & $walk $root '' 0 $state\",\r\n \" if ($state.Truncated) {\",\r\n \" Write-Host (\\\"… output capped at {0} entries (use -Limit <number> or -All)\\\" -f $state.Limit) -ForegroundColor DarkGray\",\r\n \" }\",\r\n \"}\",\r\n ],\r\n \"Adding the tree-style ls command to the Windows PowerShell profile\",\r\n );\r\n}\r\n","import { settings, type SettingValue } from \"./settings.js\";\n\nexport interface SummarySection {\n group: string;\n rows: [string, string][];\n}\n\nexport function normalizeHex(value: string): string {\n return value.trim().replace(/^#?/, \"#\").toUpperCase();\n}\n\nexport function buildSummarySections(\n answers: Record<string, SettingValue>,\n): SummarySection[] {\n const sections: SummarySection[] = [];\n let current: SummarySection | null = null;\n\n for (const setting of settings) {\n const value = answers[setting.id];\n if (value === undefined) continue;\n\n if (!current || current.group !== setting.group) {\n current = { group: setting.group, rows: [] };\n sections.push(current);\n }\n\n current.rows.push([setting.label, setting.summarize(value)]);\n }\n\n return sections;\n}\n","import {\r\n copyFileSync,\r\n existsSync,\r\n lstatSync,\r\n readFileSync,\r\n readdirSync,\r\n writeFileSync,\r\n} from \"node:fs\";\r\nimport { basename, dirname, join } from \"node:path\";\r\nimport { applyEdits, modify, parse, type ParseError } from \"jsonc-parser\";\r\n\r\nexport interface SettingsBackup {\r\n path: string;\r\n createdAt: Date;\r\n}\r\n\r\nexport class InvalidSettingsFileError extends Error {\r\n constructor() {\r\n super(\r\n \"Windows Terminal settings.json is invalid JSONC. No changes were written. Restore the file from a backup before trying again.\",\r\n );\r\n this.name = \"InvalidSettingsFileError\";\r\n }\r\n}\r\n\r\n/**\r\n * Sucht die Windows Terminal settings.json.\r\n * Prüft Stable, Preview und Canary in dieser Reihenfolge.\r\n */\r\nexport function findSettingsPath(): string | undefined {\r\n const localAppData = process.env.LOCALAPPDATA;\r\n if (!localAppData) return undefined;\r\n\r\n const candidates = [\r\n join(localAppData, \"Packages\", \"Microsoft.WindowsTerminal_8wekyb3d8bbwe\", \"LocalState\", \"settings.json\"),\r\n join(localAppData, \"Packages\", \"Microsoft.WindowsTerminalPreview_8wekyb3d8bbwe\", \"LocalState\", \"settings.json\"),\r\n join(localAppData, \"Packages\", \"Microsoft.WindowsTerminal.Canary_8wekyb3d8bbwe\", \"LocalState\", \"settings.json\"),\r\n ];\r\n\r\n for (const path of candidates) {\r\n if (existsSync(path)) return path;\r\n }\r\n\r\n return undefined;\r\n}\r\n\r\n/**\r\n * Liest die settings.json als rohen Text.\r\n */\r\nexport function readSettingsFile(settingsPath: string): string {\r\n return readFileSync(settingsPath, \"utf8\");\r\n}\r\n\r\n/**\r\n * Schreibt die geänderte settings.json zurück. Kommentare und Formatierung\r\n * werden so weit wie möglich erhalten (jsonc-parser.modify).\r\n */\r\nexport function writeSettingsFile(settingsPath: string, content: string): void {\r\n writeFileSync(settingsPath, content, \"utf8\");\r\n}\r\n\r\nexport function createSettingsBackup(settingsPath: string): string {\r\n const timestamp = Date.now();\r\n const backupPrefix = `${basename(settingsPath)}.backup-${timestamp}-`;\r\n let sequence = 0;\r\n let backupPath: string;\r\n\r\n do {\r\n backupPath = join(dirname(settingsPath), `${backupPrefix}${sequence}`);\r\n sequence += 1;\r\n } while (existsSync(backupPath));\r\n\r\n copyFileSync(settingsPath, backupPath);\r\n return backupPath;\r\n}\r\n\r\nexport function listSettingsBackups(settingsPath: string): SettingsBackup[] {\r\n const backupPrefix = `${basename(settingsPath)}.backup-`;\r\n\r\n return readdirSync(dirname(settingsPath))\r\n .filter((name) => name.startsWith(backupPrefix))\r\n .flatMap((name): SettingsBackup[] => {\r\n const match = /^(\\d+)-(\\d+)$/.exec(name.slice(backupPrefix.length));\r\n if (!match) return [];\r\n\r\n const path = join(dirname(settingsPath), name);\r\n if (!lstatSync(path).isFile()) return [];\r\n\r\n return [{ path, createdAt: new Date(Number(match[1])) }];\r\n })\r\n .sort((left, right) => right.createdAt.getTime() - left.createdAt.getTime());\r\n}\r\n\r\nexport function restoreSettingsBackup(\r\n settingsPath: string,\r\n backupPath: string,\r\n): string {\r\n const backup = listSettingsBackups(settingsPath).find(\r\n (candidate) => candidate.path === backupPath,\r\n );\r\n if (!backup) {\r\n throw new Error(\"The selected settings backup is not available.\");\r\n }\r\n\r\n const content = readFileSync(backup.path, \"utf8\");\r\n const parseErrors: ParseError[] = [];\r\n const parsedContent = parse(content, parseErrors, { allowTrailingComma: true });\r\n if (\r\n parseErrors.length > 0 ||\r\n parsedContent === null ||\r\n typeof parsedContent !== \"object\" ||\r\n Array.isArray(parsedContent)\r\n ) {\r\n throw new Error(\"The selected backup is invalid JSONC. Nothing was changed.\");\r\n }\r\n\r\n const safetyBackupPath = createSettingsBackup(settingsPath);\r\n writeSettingsFile(settingsPath, content);\r\n return safetyBackupPath;\r\n}\r\n\r\n/**\r\n * Wendet eine Änderung an der settings.json an.\r\n *\r\n * @param content - Der aktuelle Inhalt der settings.json\r\n * @param jsonPath - Pfad im JSON, z. B. [\"profiles\", \"defaults\", \"background\"]\r\n * @param value - Der neue Wert\r\n * @returns Der neu geschriebene Dateiinhalt\r\n */\r\nexport function setSetting(\r\n content: string,\r\n jsonPath: (string | number)[],\r\n value: unknown,\r\n): string {\r\n const parseErrors: ParseError[] = [];\r\n const parsedContent = parse(content, parseErrors, { allowTrailingComma: true });\r\n if (\r\n parseErrors.length > 0 ||\r\n parsedContent === null ||\r\n typeof parsedContent !== \"object\" ||\r\n Array.isArray(parsedContent)\r\n ) {\r\n throw new InvalidSettingsFileError();\r\n }\r\n\r\n const edits = modify(content, jsonPath, value, {\r\n formattingOptions: {\r\n tabSize: 4,\r\n insertSpaces: true,\r\n },\r\n });\r\n return applyEdits(content, edits);\r\n}\r\n"],"mappings":"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","names":["readFileSync","pc","parse","execFileSync","join","parse","setting","readFileSync","pc"]}
1
+ {"version":3,"sources":["../src/index.ts","../src/installer.ts","../src/settings.ts","../src/fonts.ts","../src/powershell.ts","../src/summary.ts","../src/wtsettings.ts"],"sourcesContent":["#!/usr/bin/env node\n\nimport { readFileSync } from \"node:fs\";\nimport pc from \"picocolors\";\nimport { runInstaller } from \"./installer.js\";\n\nfunction readVersion(): string {\n const pkg = JSON.parse(\n readFileSync(new URL(\"../package.json\", import.meta.url), \"utf8\"),\n ) as { version: string };\n return pkg.version;\n}\n\nfunction printHelp(): void {\n console.log(`\n${pc.bold(pc.cyan(\"pimpt\"))} ${pc.dim(\"— interactive Windows Terminal setup assistant\")}\n\n${pc.bold(\"Usage\")}\n pimpt Start the interactive installer\n pimpt --help Show this help\n pimpt --version Show the installed version\n\n${pc.bold(\"Status\")}\n Preview: preferences are collected, but settings.json is not modified yet.\n`);\n}\n\nasync function main(): Promise<void> {\n const args = process.argv.slice(2);\n\n if (args.includes(\"--help\") || args.includes(\"-h\")) {\n printHelp();\n return;\n }\n\n if (args.includes(\"--version\") || args.includes(\"-v\")) {\n console.log(`pimpt ${readVersion()}`);\n return;\n }\n\n if (args.length > 0) {\n console.error(`Unknown option: ${args[0]}`);\n printHelp();\n process.exitCode = 1;\n return;\n }\n\n await runInstaller();\n}\n\ntry {\n await main();\n} catch (error) {\n console.error(pc.red(\"pimpt failed:\"));\n console.error(error instanceof Error ? error.stack ?? error.message : String(error));\n process.exitCode = 1;\n}\n","import {\n cancel,\n confirm,\n intro,\n isCancel,\n log,\n note,\n outro,\n select,\n spinner,\n text,\n} from \"@clack/prompts\";\nimport { spawn } from \"node:child_process\";\nimport { statSync } from \"node:fs\";\nimport { parse, type ParseError } from \"jsonc-parser\";\nimport { win32 as pathWin32 } from \"node:path\";\nimport pc from \"picocolors\";\nimport { setTimeout as delay } from \"node:timers/promises\";\nimport {\n BACKGROUND_CUSTOM,\n settings,\n type SettingDefinition,\n type SettingValue,\n} from \"./settings.js\";\nimport {\n canInstallFont,\n installFont,\n installNerdFont,\n isFontInstalled,\n NERD_FONT_FAMILY,\n} from \"./fonts.js\";\nimport {\n addTerminalIconsToPowerShellProfile,\n addHistoryPreviewToPowerShellProfile,\n addTreeListingToPowerShellProfile,\n installPSReadLineModule,\n installTerminalIconsModule,\n readPowerShellProfileFeatures,\n} from \"./powershell.js\";\nimport { buildSummarySections, normalizeHex } from \"./summary.js\";\nimport {\n createSettingsBackup,\n findSettingsPath,\n InvalidSettingsFileError,\n listSettingsBackups,\n readSettingsFile,\n restoreSettingsBackup,\n setSetting,\n writeSettingsFile,\n} from \"./wtsettings.js\";\n\nconst BANNER = `\n ██████╗ ██╗███╗ ███╗██████╗ ████████╗\n ██╔══██╗██║████╗ ████║██╔══██╗╚══██╔══╝\n ██████╔╝██║██╔████╔██║██████╔╝ ██║\n ██╔═══╝ ██║██║╚██╔╝██║██╔═══╝ ██║\n ██║ ██║██║ ╚═╝ ██║██║ ██║\n ╚═╝ ╚═╝╚═╝ ╚═╝╚═╝ ╚═╝\n`;\n\nfunction bail<T>(value: T): Exclude<T, symbol> {\n if (isCancel(value)) {\n cancel(\"Setup cancelled. Nothing was changed.\");\n process.exit(0);\n }\n return value as Exclude<T, symbol>;\n}\n\nclass StartingDirectoryInputError extends Error {}\n\nfunction normalizeStartingDirectory(value: string): string {\n let directory = value.trim();\n if (!directory) return \"\";\n\n if (\n (directory.startsWith('\"') && directory.endsWith('\"')) ||\n (directory.startsWith(\"'\") && directory.endsWith(\"'\"))\n ) {\n directory = directory.slice(1, -1).trim();\n }\n if (!directory) return \"\";\n\n const userProfile = process.env.USERPROFILE ?? process.env.HOME;\n if (/^~(?=$|[\\\\/])/.test(directory)) {\n if (!userProfile) {\n throw new StartingDirectoryInputError(\n \"Cannot resolve '~' because the user folder is unknown.\",\n );\n }\n directory = directory.replace(/^~/, userProfile);\n }\n\n directory = directory.replace(/%([^%]+)%/g, (variable, name: string) => {\n const key = Object.keys(process.env).find(\n (candidate) => candidate.toLowerCase() === name.toLowerCase(),\n );\n const environmentValue = key ? process.env[key] : undefined;\n if (environmentValue === undefined) {\n throw new StartingDirectoryInputError(\n `Unknown environment variable in starting path: ${variable}`,\n );\n }\n return environmentValue;\n });\n\n if (/^[a-zA-Z]:(?![\\\\/])/.test(directory)) {\n throw new StartingDirectoryInputError(\n \"Use an absolute drive path, for example C:\\\\Users\\\\you\\\\Downloads.\",\n );\n }\n\n if (/^[\\\\/](?![\\\\/])/.test(directory)) {\n if (!userProfile) {\n throw new StartingDirectoryInputError(\n \"Cannot resolve a rooted path because the user folder is unknown.\",\n );\n }\n directory = pathWin32.resolve(pathWin32.parse(userProfile).root, directory);\n }\n\n if (pathWin32.isAbsolute(directory)) return pathWin32.normalize(directory);\n if (!userProfile) {\n throw new StartingDirectoryInputError(\n \"Cannot resolve a relative starting path because the user folder is unknown.\",\n );\n }\n return pathWin32.resolve(userProfile, directory);\n}\n\nfunction validateStartingDirectory(value: string | undefined): string | undefined {\n let directory: string;\n try {\n directory = normalizeStartingDirectory(value ?? \"\");\n } catch (error) {\n if (error instanceof StartingDirectoryInputError) return error.message;\n throw error;\n }\n\n if (!directory || process.platform !== \"win32\") return undefined;\n\n try {\n if (!statSync(directory).isDirectory()) {\n return \"The starting path must be an existing folder.\";\n }\n } catch (error) {\n if (\n error !== null &&\n typeof error === \"object\" &&\n \"code\" in error &&\n (error.code === \"ENOENT\" || error.code === \"ENOTDIR\")\n ) {\n return `Folder not found: ${directory}`;\n }\n if (\n error !== null &&\n typeof error === \"object\" &&\n \"code\" in error &&\n (error.code === \"EACCES\" || error.code === \"EPERM\")\n ) {\n return `Cannot access folder: ${directory}`;\n }\n throw error;\n }\n return undefined;\n}\n\nasync function askSetting(\n setting: SettingDefinition,\n currentValue?: SettingValue,\n): Promise<SettingValue> {\n const prompt = setting.prompt;\n\n if (prompt.kind === \"select\") {\n const selectValue = async () =>\n bail(\n await select<string>({\n message: prompt.message,\n options: prompt.options,\n initialValue: prompt.initialValue,\n }),\n );\n\n if (setting.id === \"fontFace\") {\n while (true) {\n const fontFamily = await selectValue();\n if (fontFamily === \"keep\" || isFontInstalled(fontFamily)) {\n return fontFamily;\n }\n\n if (!canInstallFont(fontFamily)) {\n log.warn(\n pc.yellow(\n `${fontFamily} is not installed and cannot be installed automatically. Choose another font.`,\n ),\n );\n continue;\n }\n\n const shouldInstall = bail(\n await confirm({\n message: `${fontFamily} is not installed. Install it now? Select No to choose another font.`,\n initialValue: true,\n }),\n );\n if (!shouldInstall) continue;\n\n const fontSpinner = spinner();\n fontSpinner.start(`Installing ${fontFamily}…`);\n try {\n await installFont(fontFamily);\n } catch (error) {\n fontSpinner.error(`Could not install ${fontFamily}.`);\n throw error;\n }\n fontSpinner.stop(\n `${fontFamily} installed. Restart Windows Terminal to use it.`,\n );\n return fontFamily;\n }\n }\n\n const value = await selectValue();\n\n // Hintergrundfarbe: bei \"Custom\" folgt eine Hex-Eingabe mit Validierung.\n if (setting.id === \"background\" && value === BACKGROUND_CUSTOM) {\n const custom = bail(\n await text({\n message: \"Enter a background color\",\n placeholder: \"#1E1E2E\",\n initialValue: \"\",\n validate: (input) => {\n const raw = input ?? \"\";\n return /^#?[0-9a-fA-F]{6}$/.test(raw.trim())\n ? undefined\n : \"Use a 6-digit hex color, e.g. #1E1E2E\";\n },\n }),\n );\n return normalizeHex(custom);\n }\n\n return value;\n }\n\n if (prompt.kind === \"text\") {\n const value = bail(\n await text({\n message: prompt.message,\n placeholder: prompt.placeholder,\n initialValue:\n currentValue === undefined ? prompt.initialValue : String(currentValue),\n ...(setting.id === \"startingDirectory\"\n ? { validate: validateStartingDirectory }\n : prompt.validate\n ? { validate: prompt.validate }\n : {}),\n }),\n );\n return setting.id === \"startingDirectory\"\n ? normalizeStartingDirectory(value)\n : value;\n }\n\n return bail(\n await confirm({\n message: prompt.message,\n initialValue: prompt.initialValue,\n }),\n );\n}\n\nfunction renderSummary(answers: Record<string, SettingValue>): void {\n const sections = buildSummarySections(answers);\n\n if (sections.length === 0) {\n note(\"No settings selected.\", \"Configuration summary\");\n return;\n }\n\n const labelWidth = Math.max(\n ...sections.flatMap((section) =>\n section.rows.map(([label]) => label.length),\n ),\n );\n\n const lines: string[] = [];\n\n sections.forEach((section, index) => {\n if (index > 0) lines.push(\"\");\n lines.push(pc.bold(pc.cyan(section.group)));\n\n for (const [label, value] of section.rows) {\n lines.push(` ${pc.dim(label.padEnd(labelWidth))} ${value}`);\n }\n });\n\n note(lines.join(\"\\n\"), \"Your configuration\");\n}\n\nfunction openNewTerminalTab(): boolean {\n if (!process.env.WT_SESSION) return false;\n\n try {\n const terminal = spawn(\"wt.exe\", [\"-w\", \"0\", \"new-tab\"], {\n detached: true,\n stdio: \"ignore\",\n windowsHide: true,\n });\n terminal.on(\"error\", (error) => {\n log.warn(\n pc.yellow(`Could not open a new Windows Terminal tab: ${error.message}`),\n );\n });\n terminal.unref();\n return true;\n } catch (error) {\n log.warn(\n pc.yellow(`Could not open a new Windows Terminal tab: ${String(error)}`),\n );\n return false;\n }\n}\n\nfunction getDefaultProfileIndex(content: string): number | undefined {\n const parsed = parse(content) as {\n defaultProfile?: unknown;\n profiles?: { list?: unknown };\n };\n if (\n typeof parsed.defaultProfile !== \"string\" ||\n !parsed.profiles ||\n typeof parsed.profiles !== \"object\" ||\n !Array.isArray(parsed.profiles.list)\n ) {\n return undefined;\n }\n\n const index = parsed.profiles.list.findIndex(\n (profile: unknown) =>\n profile !== null &&\n typeof profile === \"object\" &&\n \"guid\" in profile &&\n profile.guid === parsed.defaultProfile,\n );\n return index < 0 ? undefined : index;\n}\n\nfunction getWindowsPowerShellProfiles(\n content: string,\n): { index: number; commandline?: string }[] {\n const parseErrors: ParseError[] = [];\n const parsed: unknown = parse(content, parseErrors, {\n allowTrailingComma: true,\n });\n if (\n parseErrors.length > 0 ||\n parsed === null ||\n typeof parsed !== \"object\" ||\n Array.isArray(parsed)\n ) {\n throw new InvalidSettingsFileError();\n }\n\n const profiles = \"profiles\" in parsed ? parsed.profiles : undefined;\n if (\n profiles === null ||\n typeof profiles !== \"object\" ||\n Array.isArray(profiles) ||\n !(\"list\" in profiles) ||\n !Array.isArray(profiles.list)\n ) {\n return [];\n }\n\n return profiles.list.flatMap((profile: unknown, index: number) => {\n if (\n profile === null ||\n typeof profile !== \"object\" ||\n Array.isArray(profile)\n ) {\n return [];\n }\n\n const name =\n \"name\" in profile && typeof profile.name === \"string\"\n ? profile.name\n : \"\";\n const commandline =\n \"commandline\" in profile && typeof profile.commandline === \"string\"\n ? profile.commandline\n : undefined;\n return name.toLowerCase() === \"windows powershell\" ||\n /(?:^|[\\\\/\"])powershell\\.exe(?:[\"\\s]|$)/i.test(commandline ?? \"\")\n ? [\n {\n index,\n ...(commandline !== undefined ? { commandline } : {}),\n },\n ]\n : [];\n });\n}\n\nfunction readConfiguredAnswers(\n settingsPath: string | undefined,\n): Record<string, SettingValue> {\n const answers: Record<string, SettingValue> = {};\n try {\n const profileFeatures = readPowerShellProfileFeatures();\n if (profileFeatures.terminalIcons) answers.terminalIcons = true;\n if (profileFeatures.historyPreview) answers.historyPreview = true;\n if (profileFeatures.treeListing) answers.treeListing = true;\n } catch (error) {\n log.warn(\n pc.yellow(\n `Could not detect configured PowerShell features: ${error instanceof Error ? error.message : String(error)}`,\n ),\n );\n }\n if (!settingsPath) return answers;\n\n const content = readSettingsFile(settingsPath);\n const parseErrors: ParseError[] = [];\n const parsed: unknown = parse(content, parseErrors, {\n allowTrailingComma: true,\n });\n if (\n parseErrors.length > 0 ||\n parsed === null ||\n typeof parsed !== \"object\" ||\n Array.isArray(parsed)\n ) {\n log.warn(\n pc.yellow(\n \"Could not read existing settings.json values because the file contains invalid JSONC.\",\n ),\n );\n return answers;\n }\n\n const profiles =\n \"profiles\" in parsed && parsed.profiles !== null\n ? parsed.profiles\n : undefined;\n const profileList =\n profiles !== null &&\n typeof profiles === \"object\" &&\n !Array.isArray(profiles) &&\n \"list\" in profiles &&\n Array.isArray(profiles.list)\n ? profiles.list\n : [];\n const defaultProfileGuid =\n \"defaultProfile\" in parsed ? parsed.defaultProfile : undefined;\n const defaultProfile =\n typeof defaultProfileGuid === \"string\"\n ? profileList.find(\n (profile: unknown) =>\n profile !== null &&\n typeof profile === \"object\" &&\n !Array.isArray(profile) &&\n \"guid\" in profile &&\n profile.guid === defaultProfileGuid,\n )\n : undefined;\n const defaults =\n profiles !== null &&\n typeof profiles === \"object\" &&\n !Array.isArray(profiles) &&\n \"defaults\" in profiles\n ? profiles.defaults\n : undefined;\n\n if (defaults !== null && typeof defaults === \"object\" && !Array.isArray(defaults)) {\n if (\n \"opacity\" in defaults &&\n typeof defaults.opacity === \"number\" &&\n Number.isInteger(defaults.opacity) &&\n defaults.opacity >= 0 &&\n defaults.opacity <= 100\n ) {\n answers.transparency =\n defaults.opacity === 100 &&\n \"useAcrylic\" in defaults &&\n defaults.useAcrylic === false\n ? \"off\"\n : String(defaults.opacity);\n }\n\n if (\"background\" in defaults && typeof defaults.background === \"string\") {\n answers.background = defaults.background;\n }\n\n const defaultStartingDirectory =\n \"startingDirectory\" in defaults &&\n typeof defaults.startingDirectory === \"string\"\n ? defaults.startingDirectory\n : undefined;\n const font =\n \"font\" in defaults && defaults.font !== null\n ? defaults.font\n : undefined;\n if (\n font !== null &&\n typeof font === \"object\" &&\n !Array.isArray(font) &&\n \"face\" in font &&\n typeof font.face === \"string\"\n ) {\n answers.fontFace = font.face;\n }\n\n const profileStartingDirectory =\n defaultProfile !== null &&\n typeof defaultProfile === \"object\" &&\n !Array.isArray(defaultProfile) &&\n \"startingDirectory\" in defaultProfile &&\n typeof defaultProfile.startingDirectory === \"string\"\n ? defaultProfile.startingDirectory\n : undefined;\n const startingDirectory =\n profileStartingDirectory ?? defaultStartingDirectory;\n if (startingDirectory !== undefined) {\n const error = validateStartingDirectory(startingDirectory);\n if (error) {\n log.warn(pc.yellow(`Ignoring the saved starting directory: ${error}`));\n } else {\n answers.startingDirectory =\n normalizeStartingDirectory(startingDirectory);\n }\n }\n }\n\n const powerShellProfiles = getWindowsPowerShellProfiles(content);\n if (\n powerShellProfiles.length > 0 &&\n powerShellProfiles.every((profile) =>\n /(?:^|\\s)-NoLogo(?:\\s|$)/i.test(profile.commandline ?? \"\"),\n )\n ) {\n answers.hidePowerShellBanner = true;\n }\n\n return answers;\n}\n\n/**\n * Schreibt die Antworten in verfügbare Terminal-Einstellungen. Kommentare und\n * Formatierung der JSONC-Dateien werden erhalten.\n */\nasync function applySettings(\n answers: Record<string, SettingValue>,\n settingsPath: string | undefined = findSettingsPath(),\n): Promise<void> {\n const terminalIconsEnabled = answers.terminalIcons === true;\n const hidePowerShellBanner = answers.hidePowerShellBanner === true;\n\n if (!settingsPath) {\n if (terminalIconsEnabled) {\n throw new Error(\n \"Cannot enable PowerShell file icons because Windows Terminal settings.json could not be found.\",\n );\n }\n if (hidePowerShellBanner) {\n throw new Error(\n \"Cannot hide the PowerShell startup banner because Windows Terminal settings.json could not be found.\",\n );\n }\n log.warn(\n pc.dim(\"Could not find Windows Terminal settings.json. Skipping write.\"),\n );\n return;\n }\n\n log.info(pc.dim(`Writing to ${settingsPath}…`));\n\n const originalContent = readSettingsFile(settingsPath);\n let content = originalContent;\n for (const setting of settings) {\n const value = answers[setting.id];\n if (value === undefined) continue;\n if (!setting.jsonPath) continue;\n if (setting.skipIfKeep && value === \"keep\") continue;\n if (terminalIconsEnabled && setting.id === \"fontFace\") continue;\n\n if (setting.id === \"transparency\") {\n const opacity = value === \"off\" ? 100 : Number(value);\n if (!Number.isInteger(opacity) || opacity < 0 || opacity > 100) {\n throw new Error(`Invalid transparency value: ${String(value)}`);\n }\n\n content = setSetting(content, setting.jsonPath, opacity);\n content = setSetting(\n content,\n [\"profiles\", \"defaults\", \"useAcrylic\"],\n value !== \"off\",\n );\n content = setSetting(\n content,\n [\"useAcrylicInTabRow\"],\n value !== \"off\",\n );\n } else if (setting.id === \"background\") {\n content = setSetting(content, setting.jsonPath, value);\n content = setSetting(\n content,\n [\"profiles\", \"defaults\", \"tabColor\"],\n value,\n );\n } else if (setting.id === \"fontFace\") {\n const defaultProfileIndex = getDefaultProfileIndex(content);\n content = setSetting(content, setting.jsonPath, value);\n if (defaultProfileIndex !== undefined) {\n content = setSetting(\n content,\n [\"profiles\", \"list\", defaultProfileIndex, \"font\", \"face\"],\n value,\n );\n }\n } else if (setting.id === \"startingDirectory\") {\n const defaultProfileIndex = getDefaultProfileIndex(content);\n const startingDirectory = String(value).trim() || undefined;\n content = setSetting(content, setting.jsonPath, startingDirectory);\n if (defaultProfileIndex !== undefined) {\n content = setSetting(\n content,\n [\"profiles\", \"list\", defaultProfileIndex, \"startingDirectory\"],\n startingDirectory,\n );\n }\n } else {\n content = setSetting(content, setting.jsonPath, value);\n }\n }\n\n if (hidePowerShellBanner) {\n const powerShellProfiles = getWindowsPowerShellProfiles(content);\n if (powerShellProfiles.length === 0) {\n throw new Error(\n \"Cannot hide the PowerShell startup banner because no Windows PowerShell profile was found.\",\n );\n }\n\n for (const profile of powerShellProfiles) {\n const commandline =\n profile.commandline?.trim()\n ? profile.commandline\n : \"powershell.exe\";\n if (/(?:^|\\s)-NoLogo(?:\\s|$)/i.test(commandline)) continue;\n\n content = setSetting(\n content,\n [\"profiles\", \"list\", profile.index, \"commandline\"],\n `${commandline} -NoLogo`,\n );\n }\n }\n\n if (terminalIconsEnabled) {\n const defaultProfileIndex = getDefaultProfileIndex(content);\n content = setSetting(\n content,\n [\"profiles\", \"defaults\", \"font\", \"face\"],\n NERD_FONT_FAMILY,\n );\n if (defaultProfileIndex !== undefined) {\n content = setSetting(\n content,\n [\"profiles\", \"list\", defaultProfileIndex, \"font\", \"face\"],\n NERD_FONT_FAMILY,\n );\n }\n }\n\n if (terminalIconsEnabled) {\n await installNerdFont();\n installTerminalIconsModule();\n }\n\n const dirty = content !== originalContent;\n if (dirty) {\n const backupPath = createSettingsBackup(settingsPath);\n log.info(pc.dim(`Backup created at ${backupPath}`));\n writeSettingsFile(settingsPath, content);\n }\n\n if (terminalIconsEnabled) {\n addTerminalIconsToPowerShellProfile();\n }\n}\n\nexport async function runInstaller(): Promise<void> {\n console.log(pc.cyan(BANNER));\n intro(pc.bold(\"Pimp up your Terminal.\"));\n\n const selectableSettings = settings.filter(\n (setting) =>\n (setting.group === \"Appearance\" &&\n (setting.jsonPath !== undefined ||\n setting.id === \"terminalIcons\" ||\n setting.id === \"hidePowerShellBanner\")) ||\n (setting.group === \"Features\" &&\n (setting.jsonPath !== undefined ||\n setting.id === \"historyPreview\" ||\n setting.id === \"treeListing\")),\n );\n const settingsPath = findSettingsPath();\n const backups = settingsPath ? listSettingsBackups(settingsPath) : [];\n const answers = readConfiguredAnswers(settingsPath);\n let initialPickerValue = selectableSettings[0]?.id;\n let initialArea = \"Appearance\";\n\n while (true) {\n const areaOptions = [\n { value: \"Appearance\", label: \"Appearance\", hint: \"Colors and profile settings\" },\n { value: \"Features\", label: \"Features\", hint: \"Optional extras\" },\n { value: \"Other\", label: \"Other\", hint: \"Backups and recovery\" },\n ];\n if (Object.keys(answers).length > 0) {\n areaOptions.push({\n value: \"done\",\n label: \"Done\",\n hint: \"Review and apply your settings\",\n });\n }\n\n const selectedArea = bail(\n await select<string>({\n message: \"Choose an area\",\n options: areaOptions,\n initialValue: initialArea,\n }),\n );\n if (selectedArea === \"done\") break;\n\n initialArea = selectedArea;\n if (selectedArea === \"Other\") {\n if (backups.length === 0) {\n note(\n \"No backups yet. pimpt creates one before changing settings.json.\",\n \"Other\",\n );\n continue;\n }\n\n const selectedAction = bail(\n await select<string>({\n message: \"Other\",\n options: [\n {\n value: \"restoreBackup\",\n label: \"Restore settings backup\",\n hint: \"Choose a saved version\",\n },\n { value: \"back\", label: \"Back\", hint: \"Choose another area\" },\n ],\n initialValue: \"restoreBackup\",\n }),\n );\n if (selectedAction === \"back\") continue;\n if (!settingsPath) {\n throw new Error(\"Windows Terminal settings.json could not be found.\");\n }\n\n const selectedBackup = bail(\n await select<string>({\n message: \"Which backup should be restored?\",\n options: backups.map((backup) => ({\n value: backup.path,\n label: backup.createdAt.toLocaleString(),\n hint: backup.path,\n })),\n ...(backups[0] ? { initialValue: backups[0].path } : {}),\n }),\n );\n const shouldRestore = bail(\n await confirm({\n message:\n \"This replaces settings.json. The current file will be backed up first. Continue?\",\n initialValue: false,\n }),\n );\n if (!shouldRestore) continue;\n\n const restoreSpinner = spinner();\n restoreSpinner.start(\"Restoring settings.json backup…\");\n try {\n const safetyBackupPath = restoreSettingsBackup(\n settingsPath,\n selectedBackup,\n );\n restoreSpinner.stop(\"Settings restored successfully.\");\n log.info(\n pc.dim(`The previous settings were backed up to ${safetyBackupPath}`),\n );\n outro(pc.green(\"✓ Windows Terminal settings.json was restored.\"));\n } catch (error) {\n restoreSpinner.error(\"Could not restore the settings backup.\");\n throw error;\n }\n return;\n }\n\n while (true) {\n const visibleSettings = selectableSettings.filter(\n (setting) =>\n setting.group === selectedArea &&\n !(answers.terminalIcons === true && setting.id === \"fontFace\"),\n );\n const options = visibleSettings.map((setting) => ({\n value: setting.id,\n label:\n answers[setting.id] === undefined\n ? setting.label\n : `${pc.green(\"●\")} ${setting.label}`,\n hint: setting.hint,\n }));\n options.push({\n value: \"back\",\n label: \"Back\",\n hint: \"Choose another area\",\n });\n\n const firstOption = options[0];\n if (!firstOption) {\n throw new Error(`No settings are available in ${selectedArea}.`);\n }\n\n const selectedInitialValue =\n initialPickerValue &&\n options.some((option) => option.value === initialPickerValue)\n ? initialPickerValue\n : firstOption.value;\n const selectedId = bail(\n await select<string>({\n message: selectedArea,\n options,\n initialValue: selectedInitialValue,\n }),\n );\n if (selectedId === \"back\") break;\n\n const setting = selectableSettings.find(\n (candidate) =>\n candidate.id === selectedId && candidate.group === selectedArea,\n );\n if (!setting) {\n throw new Error(\n `Unknown setting selected in ${selectedArea}: ${selectedId}`,\n );\n }\n\n initialPickerValue = selectedId;\n log.step(pc.bold(pc.cyan(setting.group)));\n answers[setting.id] = await askSetting(setting, answers[setting.id]);\n if (setting.id === \"terminalIcons\" && answers.terminalIcons === true) {\n answers.fontFace = NERD_FONT_FAMILY;\n initialPickerValue = \"terminalIcons\";\n }\n }\n }\n\n renderSummary(answers);\n\n const proceed = bail(\n await confirm({\n message: \"Install these settings? (writes to settings.json)\",\n initialValue: true,\n }),\n );\n\n if (!proceed) {\n cancel(\"Setup cancelled. Nothing was changed.\");\n return;\n }\n\n const s = spinner();\n s.start(\"Building your configuration…\");\n await delay(300);\n s.message(\"Checking compatibility…\");\n await delay(300);\n s.message(\n answers.terminalIcons === true ||\n answers.historyPreview === true ||\n answers.treeListing === true ||\n answers.hidePowerShellBanner === true\n ? \"Applying PowerShell options…\"\n : \"Writing settings.json…\",\n );\n await delay(400);\n\n try {\n await applySettings(answers, settingsPath);\n if (answers.historyPreview === true) {\n installPSReadLineModule();\n addHistoryPreviewToPowerShellProfile();\n }\n if (answers.treeListing === true) {\n addTreeListingToPowerShellProfile();\n }\n } catch (error) {\n if (!(error instanceof InvalidSettingsFileError)) throw error;\n\n s.error(error.message);\n process.exitCode = 1;\n return;\n }\n\n s.stop(\"Configuration applied successfully.\");\n\n const fontSelected =\n answers.fontFace !== undefined && answers.fontFace !== \"keep\";\n const powerShellFeatureSelected =\n answers.terminalIcons === true ||\n answers.historyPreview === true ||\n answers.treeListing === true ||\n answers.hidePowerShellBanner === true;\n if (fontSelected || powerShellFeatureSelected) openNewTerminalTab();\n outro(\n [\n `${pc.green(\"✓\")} Your configuration is ready.`,\n pc.dim(\"Your selected settings and features are ready.\"),\n ].join(\"\\n\"),\n );\n}\n","export type SettingValue = string | boolean;\n\nexport type SettingGroup =\n | \"Appearance\"\n | \"Colors\"\n | \"Window & tabs\"\n | \"Profile\"\n | \"Behavior\"\n | \"Features\"\n | \"Other\";\n\nexport interface Choice {\n value: string;\n label: string;\n hint: string;\n}\n\nexport type Prompt =\n | {\n kind: \"select\";\n message: string;\n options: Choice[];\n initialValue: string;\n }\n | {\n kind: \"text\";\n message: string;\n placeholder: string;\n initialValue: string;\n validate?: (value: string | undefined) => string | undefined;\n }\n | {\n kind: \"confirm\";\n message: string;\n initialValue: boolean;\n };\n\nexport interface SettingDefinition {\n id: string;\n group: SettingGroup;\n label: string;\n hint: string;\n prompt: Prompt;\n summarize: (value: SettingValue) => string;\n /**\n * Pfad in der settings.json, an dem der Wert gespeichert wird.\n * z. B. [\"profiles\", \"defaults\", \"background\"]\n * Wenn undefined, wird das Setting nicht geschrieben.\n */\n jsonPath?: string[];\n /**\n * Wenn true, wird der Wert nur geschrieben, wenn er nicht \"keep\" ist.\n * Nutzt für Presets mit \"keep\"-Option.\n */\n skipIfKeep?: boolean;\n}\n\nexport const BACKGROUND_CUSTOM = \"custom\";\n\nconst transparencyOptions: Choice[] = [\n { value: \"off\", label: \"Off\", hint: \"Solid background\" },\n { value: \"90\", label: \"Subtle\", hint: \"90% opacity\" },\n { value: \"80\", label: \"Balanced\", hint: \"80% opacity\" },\n { value: \"70\", label: \"Frosted\", hint: \"70% opacity\" },\n { value: \"50\", label: \"Heavy\", hint: \"50% opacity\" },\n { value: \"0\", label: \"Fully transparent\", hint: \"Content 0%; tab row 50% acrylic\" },\n];\n\nconst backgroundOptions: Choice[] = [\n { value: \"keep\", label: \"Keep current\", hint: \"Leave the background unchanged\" },\n { value: \"#0B1021\", label: \"Midnight\", hint: \"#0B1021\" },\n { value: \"#2E3440\", label: \"Nord\", hint: \"#2E3440\" },\n { value: \"#282A36\", label: \"Dracula\", hint: \"#282A36\" },\n { value: \"#002B36\", label: \"Solarized Dark\", hint: \"#002B36\" },\n {\n value: BACKGROUND_CUSTOM,\n label: \"Custom hex\",\n hint: \"Enter your own color\",\n },\n];\n\nconst fontOptions: Choice[] = [\n { value: \"keep\", label: \"Keep current\", hint: \"Use the configured font\" },\n { value: \"Cascadia Mono\", label: \"Cascadia Mono\", hint: \"Windows Terminal default\" },\n { value: \"Cascadia Code\", label: \"Cascadia Code\", hint: \"Ligatures included\" },\n { value: \"Consolas\", label: \"Consolas\", hint: \"Classic Windows font\" },\n { value: \"JetBrains Mono\", label: \"JetBrains Mono\", hint: \"Popular developer font\" },\n { value: \"Fira Code\", label: \"Fira Code\", hint: \"Monospace with ligatures\" },\n { value: \"Hack\", label: \"Hack\", hint: \"Designed for source code\" },\n { value: \"Source Code Pro\", label: \"Source Code Pro\", hint: \"Adobe's monospace font\" },\n { value: \"IBM Plex Mono\", label: \"IBM Plex Mono\", hint: \"Technical, readable monospace\" },\n];\n\nconst fontSizeOptions: Choice[] = [\"10\", \"11\", \"12\", \"14\", \"16\", \"18\"].map(\n (value) => ({ value, label: `${value} pt`, hint: \"Points\" }),\n);\n\nconst cursorOptions: Choice[] = [\n { value: \"keep\", label: \"Keep current\", hint: \"Use the configured cursor\" },\n { value: \"bar\", label: \"Bar\", hint: \"Thin vertical line\" },\n { value: \"filledBox\", label: \"Block\", hint: \"Filled rectangle\" },\n { value: \"underscore\", label: \"Underline\", hint: \"Line below the text\" },\n { value: \"vintage\", label: \"Vintage\", hint: \"Retro terminal blink\" },\n];\n\nconst schemeOptions: Choice[] = [\n { value: \"keep\", label: \"Keep current\", hint: \"Use the configured scheme\" },\n { value: \"Campbell\", label: \"Campbell\", hint: \"Windows Terminal default\" },\n { value: \"One Half Dark\", label: \"One Half Dark\", hint: \"Cool, muted palette\" },\n { value: \"Solarized Dark\", label: \"Solarized Dark\", hint: \"Low-contrast classic\" },\n { value: \"Tango Dark\", label: \"Tango Dark\", hint: \"Colorful and warm\" },\n { value: \"Vintage\", label: \"Vintage\", hint: \"Retro phosphor look\" },\n];\n\nconst launchModeOptions: Choice[] = [\n { value: \"default\", label: \"Windowed\", hint: \"Normal window\" },\n { value: \"maximized\", label: \"Maximized\", hint: \"Fill the screen\" },\n { value: \"fullscreen\", label: \"Fullscreen\", hint: \"Hide the window frame\" },\n { value: \"focus\", label: \"Focus mode\", hint: \"Minimal distractions\" },\n {\n value: \"maximizedFocus\",\n label: \"Maximized focus\",\n hint: \"Maximized and distraction-free\",\n },\n];\n\nconst appThemeOptions: Choice[] = [\n { value: \"system\", label: \"System\", hint: \"Follow Windows\" },\n { value: \"dark\", label: \"Dark\", hint: \"Always dark\" },\n { value: \"light\", label: \"Light\", hint: \"Always light\" },\n];\n\nconst tabLayoutOptions: Choice[] = [\n { value: \"titlebar\", label: \"Tabs in titlebar\", hint: \"Compact, modern layout\" },\n { value: \"separate\", label: \"Separate tab row\", hint: \"Tabs below the titlebar\" },\n];\n\nconst tabWidthOptions: Choice[] = [\n { value: \"equal\", label: \"Equal\", hint: \"All tabs share the width\" },\n { value: \"titleLength\", label: \"Title length\", hint: \"Width fits the title\" },\n { value: \"compact\", label: \"Compact\", hint: \"Shrink to fit\" },\n];\n\nconst iconOptions: Choice[] = [\n { value: \"classic\", label: \"Classic terminal\", hint: \"Monochrome prompt glyph\" },\n { value: \"rocket\", label: \"Rocket\", hint: \"Launch-ready\" },\n { value: \"bolt\", label: \"Bolt\", hint: \"Fast and loud\" },\n { value: \"code\", label: \"Code\", hint: \"Developer vibes\" },\n];\n\nfunction labelOf(options: Choice[], value: string): string {\n return options.find((option) => option.value === value)?.label ?? value;\n}\n\nfunction onOff(value: SettingValue): string {\n return value === true ? \"Enabled\" : \"Disabled\";\n}\n\nexport const settings: SettingDefinition[] = [\n {\n id: \"transparency\",\n group: \"Appearance\",\n label: \"Transparency\",\n hint: \"Window opacity\",\n prompt: {\n kind: \"select\",\n message: \"How transparent should the window be?\",\n options: transparencyOptions,\n initialValue: \"80\",\n },\n summarize: (value) => {\n if (value === \"off\") return \"Off\";\n if (value === \"0\") return \"Fully transparent content\";\n return `Acrylic · ${String(value)}% opacity`;\n },\n jsonPath: [\"profiles\", \"defaults\", \"opacity\"],\n },\n {\n id: \"background\",\n group: \"Appearance\",\n label: \"Background color\",\n hint: \"Preset or custom color\",\n prompt: {\n kind: \"select\",\n message: \"Pick a background color\",\n options: backgroundOptions,\n initialValue: \"keep\",\n },\n summarize: (value) => {\n if (value === \"keep\") return \"Keep current\";\n const preset = backgroundOptions.find(\n (option) => option.value === value && option.value !== \"keep\" && option.value !== BACKGROUND_CUSTOM,\n );\n return preset ? `${preset.label} (${preset.value})` : `Custom (${String(value)})`;\n },\n jsonPath: [\"profiles\", \"defaults\", \"background\"],\n skipIfKeep: true,\n },\n {\n id: \"backgroundImage\",\n group: \"Appearance\",\n label: \"Background image\",\n hint: \"Path to a local image\",\n prompt: {\n kind: \"text\",\n message: \"Path to a background image (leave empty to skip)\",\n placeholder: \"C:\\\\Users\\\\you\\\\wallpaper.png\",\n initialValue: \"\",\n },\n summarize: (value) => (String(value).trim() ? String(value) : \"Not set\"),\n },\n {\n id: \"fontFace\",\n group: \"Appearance\",\n label: \"Font\",\n hint: \"Terminal font\",\n prompt: {\n kind: \"select\",\n message: \"Choose a font\",\n options: fontOptions,\n initialValue: \"keep\",\n },\n summarize: (value) => labelOf(fontOptions, String(value)),\n jsonPath: [\"profiles\", \"defaults\", \"font\", \"face\"],\n skipIfKeep: true,\n },\n {\n id: \"fontSize\",\n group: \"Appearance\",\n label: \"Font size\",\n hint: \"Text size in points\",\n prompt: {\n kind: \"select\",\n message: \"Choose a font size\",\n options: fontSizeOptions,\n initialValue: \"12\",\n },\n summarize: (value) => `${String(value)} pt`,\n },\n {\n id: \"cursorShape\",\n group: \"Appearance\",\n label: \"Cursor\",\n hint: \"Shape of the text cursor\",\n prompt: {\n kind: \"select\",\n message: \"Choose a cursor shape\",\n options: cursorOptions,\n initialValue: \"keep\",\n },\n summarize: (value) => labelOf(cursorOptions, String(value)),\n },\n {\n id: \"colorScheme\",\n group: \"Colors\",\n label: \"Color scheme\",\n hint: \"ANSI palette for text and accents\",\n prompt: {\n kind: \"select\",\n message: \"Choose a color scheme\",\n options: schemeOptions,\n initialValue: \"keep\",\n },\n summarize: (value) => labelOf(schemeOptions, String(value)),\n },\n {\n id: \"launchMode\",\n group: \"Window & tabs\",\n label: \"Launch mode\",\n hint: \"How the window opens\",\n prompt: {\n kind: \"select\",\n message: \"How should Windows Terminal open?\",\n options: launchModeOptions,\n initialValue: \"default\",\n },\n summarize: (value) => labelOf(launchModeOptions, String(value)),\n },\n {\n id: \"appTheme\",\n group: \"Window & tabs\",\n label: \"Application theme\",\n hint: \"Light, dark, or follow Windows\",\n prompt: {\n kind: \"select\",\n message: \"Choose the application theme\",\n options: appThemeOptions,\n initialValue: \"system\",\n },\n summarize: (value) => labelOf(appThemeOptions, String(value)),\n },\n {\n id: \"tabLayout\",\n group: \"Window & tabs\",\n label: \"Tab bar\",\n hint: \"Where the tab row is displayed\",\n prompt: {\n kind: \"select\",\n message: \"Where should the tab bar live?\",\n options: tabLayoutOptions,\n initialValue: \"titlebar\",\n },\n summarize: (value) => labelOf(tabLayoutOptions, String(value)),\n },\n {\n id: \"tabWidthMode\",\n group: \"Window & tabs\",\n label: \"Tab width\",\n hint: \"How tab widths are calculated\",\n prompt: {\n kind: \"select\",\n message: \"How should tabs be sized?\",\n options: tabWidthOptions,\n initialValue: \"equal\",\n },\n summarize: (value) => labelOf(tabWidthOptions, String(value)),\n },\n {\n id: \"icon\",\n group: \"Profile\",\n label: \"Profile icon\",\n hint: \"Icon style for your profile\",\n prompt: {\n kind: \"select\",\n message: \"Pick a profile icon style\",\n options: iconOptions,\n initialValue: \"classic\",\n },\n summarize: (value) => labelOf(iconOptions, String(value)),\n },\n {\n id: \"tabTitle\",\n group: \"Profile\",\n label: \"Tab title\",\n hint: \"Custom title shown on the tab\",\n prompt: {\n kind: \"text\",\n message: \"Custom tab title (leave empty for automatic)\",\n placeholder: \"pimpt\",\n initialValue: \"\",\n },\n summarize: (value) => (String(value).trim() ? String(value) : \"Automatic\"),\n },\n {\n id: \"startingDirectory\",\n group: \"Features\",\n label: \"Starting directory\",\n hint: \"Default shell folder\",\n prompt: {\n kind: \"text\",\n message: \"Enter or paste a path; relative paths start in your user folder\",\n placeholder: \"C:\\\\Users\\\\you\\\\Projects\",\n initialValue: \"\",\n },\n summarize: (value) => (String(value).trim() ? String(value) : \"Default\"),\n jsonPath: [\"profiles\", \"defaults\", \"startingDirectory\"],\n },\n {\n id: \"copyOnSelect\",\n group: \"Behavior\",\n label: \"Copy on select\",\n hint: \"Copy text as soon as it is selected\",\n prompt: {\n kind: \"confirm\",\n message: \"Copy text automatically when selected?\",\n initialValue: false,\n },\n summarize: onOff,\n },\n {\n id: \"confirmClose\",\n group: \"Behavior\",\n label: \"Confirm close\",\n hint: \"Ask before closing multiple tabs\",\n prompt: {\n kind: \"confirm\",\n message: \"Confirm before closing a window with many tabs?\",\n initialValue: true,\n },\n summarize: onOff,\n },\n {\n id: \"terminalIcons\",\n group: \"Appearance\",\n label: \"PowerShell file icons\",\n hint: \"File icons in PowerShell\",\n prompt: {\n kind: \"confirm\",\n message:\n \"Enable PowerShell file icons? This installs Terminal-Icons and Hack Nerd Font Mono if needed, adds it to your PowerShell profile, and switches Windows Terminal to that font.\",\n initialValue: true,\n },\n summarize: onOff,\n },\n {\n id: \"historyPreview\",\n group: \"Features\",\n label: \"Command history preview\",\n hint: \"Browse recent commands\",\n prompt: {\n kind: \"confirm\",\n message:\n \"Enable a scrollable PowerShell history list? This installs PSReadLine if needed and lets the Up and Down arrows browse the visible history suggestions.\",\n initialValue: true,\n },\n summarize: onOff,\n },\n {\n id: \"treeListing\",\n group: \"Features\",\n label: \"Tree-style ls\",\n hint: \"Show files in a colored directory tree\",\n prompt: {\n kind: \"confirm\",\n message:\n \"Show directory contents as a colored tree when you run ls? Output is capped at 50 entries by default. Use -Limit or -All for more. Get-ChildItem remains available as gci.\",\n initialValue: true,\n },\n summarize: onOff,\n },\n {\n id: \"hidePowerShellBanner\",\n group: \"Appearance\",\n label: \"Hide PowerShell startup banner\",\n hint: \"Hide the welcome text\",\n prompt: {\n kind: \"confirm\",\n message: \"Hide the Windows PowerShell startup banner?\",\n initialValue: true,\n },\n summarize: onOff,\n },\n {\n id: \"focusFollowMouse\",\n group: \"Behavior\",\n label: \"Focus follows mouse\",\n hint: \"Focus panes on hover\",\n prompt: {\n kind: \"confirm\",\n message: \"Focus panes when hovering with the mouse?\",\n initialValue: false,\n },\n summarize: onOff,\n },\n {\n id: \"trimPaste\",\n group: \"Behavior\",\n label: \"Trim paste\",\n hint: \"Remove trailing whitespace when pasting\",\n prompt: {\n kind: \"confirm\",\n message: \"Trim trailing whitespace when pasting?\",\n initialValue: true,\n },\n summarize: onOff,\n },\n];\n\nexport const groupOrder: SettingGroup[] = [\n \"Appearance\",\n \"Colors\",\n \"Window & tabs\",\n \"Profile\",\n \"Behavior\",\n \"Features\",\n \"Other\",\n];\n\nexport function buildGroupedOptions(): Record<string, Choice[]> {\n const grouped: Record<string, Choice[]> = {};\n\n for (const group of groupOrder) {\n grouped[group] = settings\n .filter((setting) => setting.group === group)\n .map((setting) => ({\n value: setting.id,\n label: setting.label,\n hint: setting.hint,\n }));\n }\n\n return grouped;\n}\n","import { createHash } from \"node:crypto\";\nimport { execFileSync, spawnSync } from \"node:child_process\";\nimport { mkdir, mkdtemp, rm, writeFile } from \"node:fs/promises\";\nimport { tmpdir } from \"node:os\";\nimport { join, resolve } from \"node:path\";\n\ninterface FontAsset {\n fileName: string;\n fontUrl: string;\n licenseFileName: string;\n licenseUrl: string;\n}\n\nconst googleFontsRevision = \"29b4ec6df2522a8aee279414b78a07910b065874\";\nconst hackRevision = \"a737c121cabb337fdfe655d8c7304729f351e30f\";\nconst fontRegistryKeys = [\n \"HKLM\\\\SOFTWARE\\\\Microsoft\\\\Windows NT\\\\CurrentVersion\\\\Fonts\",\n \"HKCU\\\\SOFTWARE\\\\Microsoft\\\\Windows NT\\\\CurrentVersion\\\\Fonts\",\n];\nconst userFontsRegistryKey =\n \"HKCU\\\\SOFTWARE\\\\Microsoft\\\\Windows NT\\\\CurrentVersion\\\\Fonts\";\nexport const NERD_FONT_FAMILY = \"Hack Nerd Font Mono\";\nconst nerdFontArchive = {\n fileName: \"Hack.tar.xz\",\n url: \"https://github.com/ryanoasis/nerd-fonts/releases/download/v3.5.1/Hack.tar.xz\",\n sha256: \"cdd389472e10e2261520140ff1b382b4f8a226af5fd0b2735b975d31151d9c3c\",\n fontEntry: \"HackNerdFontMono-Regular.ttf\",\n licenseEntry: \"LICENSE.md\",\n};\n\nconst fontAssets: Record<string, FontAsset> = {\n \"Cascadia Mono\": {\n fileName: `pimpt-cascadia-mono-${googleFontsRevision.slice(0, 8)}.ttf`,\n fontUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/cascadiamono/CascadiaMono%5Bwght%5D.ttf`,\n licenseFileName: \"pimpt-cascadia-mono-OFL.txt\",\n licenseUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/cascadiamono/OFL.txt`,\n },\n \"Cascadia Code\": {\n fileName: `pimpt-cascadia-code-${googleFontsRevision.slice(0, 8)}.ttf`,\n fontUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/cascadiacode/CascadiaCode%5Bwght%5D.ttf`,\n licenseFileName: \"pimpt-cascadia-code-OFL.txt\",\n licenseUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/cascadiacode/OFL.txt`,\n },\n \"JetBrains Mono\": {\n fileName: `pimpt-jetbrains-mono-${googleFontsRevision.slice(0, 8)}.ttf`,\n fontUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/jetbrainsmono/JetBrainsMono%5Bwght%5D.ttf`,\n licenseFileName: \"pimpt-jetbrains-mono-OFL.txt\",\n licenseUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/jetbrainsmono/OFL.txt`,\n },\n \"Fira Code\": {\n fileName: `pimpt-fira-code-${googleFontsRevision.slice(0, 8)}.ttf`,\n fontUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/firacode/FiraCode%5Bwght%5D.ttf`,\n licenseFileName: \"pimpt-fira-code-OFL.txt\",\n licenseUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/firacode/OFL.txt`,\n },\n Hack: {\n fileName: `pimpt-hack-${hackRevision.slice(0, 8)}.ttf`,\n fontUrl: `https://raw.githubusercontent.com/source-foundry/Hack/${hackRevision}/build/ttf/Hack-Regular.ttf`,\n licenseFileName: \"pimpt-hack-LICENSE.md\",\n licenseUrl: `https://raw.githubusercontent.com/source-foundry/Hack/${hackRevision}/LICENSE.md`,\n },\n \"Source Code Pro\": {\n fileName: `pimpt-source-code-pro-${googleFontsRevision.slice(0, 8)}.ttf`,\n fontUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/sourcecodepro/SourceCodePro%5Bwght%5D.ttf`,\n licenseFileName: \"pimpt-source-code-pro-OFL.txt\",\n licenseUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/sourcecodepro/OFL.txt`,\n },\n \"IBM Plex Mono\": {\n fileName: `pimpt-ibm-plex-mono-${googleFontsRevision.slice(0, 8)}.ttf`,\n fontUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/ibmplexmono/IBMPlexMono-Regular.ttf`,\n licenseFileName: \"pimpt-ibm-plex-mono-OFL.txt\",\n licenseUrl: `https://raw.githubusercontent.com/google/fonts/${googleFontsRevision}/ofl/ibmplexmono/OFL.txt`,\n },\n};\n\nfunction assertWindows(): void {\n if (process.platform !== \"win32\") {\n throw new Error(\"Automatic font installation is only available on Windows.\");\n }\n}\n\nfunction queryFontRegistry(key: string): string {\n const result = spawnSync(\"reg.exe\", [\"query\", key], {\n encoding: \"utf8\",\n windowsHide: true,\n });\n if (result.error) {\n throw new Error(`Could not query the Windows font registry: ${result.error.message}`, {\n cause: result.error,\n });\n }\n if (result.status === 1) return \"\";\n if (result.status !== 0) {\n throw new Error(\n `Could not query the Windows font registry: ${result.stderr.trim() || `reg.exe exited with code ${String(result.status)}`}`,\n );\n }\n return result.stdout;\n}\n\nexport function isFontInstalled(fontFamily: string): boolean {\n assertWindows();\n const family = fontFamily.toLocaleLowerCase(\"en-US\");\n return fontRegistryKeys\n .map(queryFontRegistry)\n .join(\"\\n\")\n .split(/\\r?\\n/)\n .some((line) => line.trimStart().toLocaleLowerCase(\"en-US\").startsWith(family));\n}\n\nexport function canInstallFont(fontFamily: string): boolean {\n return fontAssets[fontFamily] !== undefined;\n}\n\nasync function download(url: string, description: string): Promise<Buffer> {\n let response: Response;\n try {\n response = await fetch(url, { signal: AbortSignal.timeout(30_000) });\n } catch (error) {\n throw new Error(`Could not download ${description}: ${String(error)}`, {\n cause: error,\n });\n }\n\n if (!response.ok) {\n throw new Error(`Could not download ${description}: HTTP ${response.status}.`);\n }\n\n const data = Buffer.from(await response.arrayBuffer());\n if (data.length === 0 || data.length > 30_000_000) {\n throw new Error(`Downloaded ${description} has an invalid file size.`);\n }\n return data;\n}\n\nfunction isFontFile(data: Buffer): boolean {\n return (\n (data[0] === 0 && data[1] === 1 && data[2] === 0 && data[3] === 0) ||\n data.toString(\"ascii\", 0, 4) === \"OTTO\"\n );\n}\n\nasync function saveAndRegisterFont(\n localAppData: string,\n fontFamily: string,\n fileName: string,\n licenseFileName: string,\n fontData: Buffer,\n licenseData: Buffer,\n): Promise<void> {\n if (!isFontFile(fontData)) {\n throw new Error(\n `The downloaded ${fontFamily} file is not a valid TrueType/OpenType font.`,\n );\n }\n\n const licenseText = licenseData.toString(\"utf8\").toLowerCase();\n if (!licenseText.includes(\"license\")) {\n throw new Error(`The downloaded ${fontFamily} license file is invalid.`);\n }\n\n const fontDirectory = join(localAppData, \"Microsoft\", \"Windows\", \"Fonts\");\n await mkdir(fontDirectory, { recursive: true });\n\n const fontPath = join(fontDirectory, fileName);\n const licensePath = join(fontDirectory, licenseFileName);\n await writeFile(fontPath, fontData);\n await writeFile(licensePath, licenseData);\n\n execFileSync(\n \"reg.exe\",\n [\n \"add\",\n userFontsRegistryKey,\n \"/v\",\n `${fontFamily} (TrueType)`,\n \"/t\",\n \"REG_SZ\",\n \"/d\",\n fontPath,\n \"/f\",\n ],\n { encoding: \"utf8\", windowsHide: true, stdio: \"pipe\" },\n );\n}\n\nexport async function installFont(fontFamily: string): Promise<void> {\n assertWindows();\n const asset = fontAssets[fontFamily];\n if (!asset) {\n throw new Error(`Automatic installation is not supported for ${fontFamily}.`);\n }\n\n const localAppData = process.env.LOCALAPPDATA;\n if (!localAppData) {\n throw new Error(\"LOCALAPPDATA is not set; the font cannot be installed.\");\n }\n\n const [fontData, licenseData] = await Promise.all([\n download(asset.fontUrl, `${fontFamily} font`),\n download(asset.licenseUrl, `${fontFamily} license`),\n ]);\n await saveAndRegisterFont(\n localAppData,\n fontFamily,\n asset.fileName,\n asset.licenseFileName,\n fontData,\n licenseData,\n );\n}\n\nexport async function installNerdFont(): Promise<void> {\n assertWindows();\n if (isFontInstalled(NERD_FONT_FAMILY)) return;\n\n const localAppData = process.env.LOCALAPPDATA;\n if (!localAppData) {\n throw new Error(\"LOCALAPPDATA is not set; the font cannot be installed.\");\n }\n\n const archiveData = await download(nerdFontArchive.url, \"Hack Nerd Font archive\");\n const actualHash = createHash(\"sha256\").update(archiveData).digest(\"hex\");\n if (actualHash !== nerdFontArchive.sha256) {\n throw new Error(\"The downloaded Hack Nerd Font archive failed its SHA-256 check.\");\n }\n\n const temporaryDirectory = await mkdtemp(join(tmpdir(), \"pimpt-nerd-font-\"));\n const archivePath = resolve(temporaryDirectory, nerdFontArchive.fileName);\n try {\n await writeFile(archivePath, archiveData);\n let fontData: Buffer;\n let licenseData: Buffer;\n try {\n fontData = execFileSync(\n \"tar.exe\",\n [\"-xOf\", archivePath, nerdFontArchive.fontEntry],\n { maxBuffer: 10_000_000, windowsHide: true },\n );\n licenseData = execFileSync(\n \"tar.exe\",\n [\"-xOf\", archivePath, nerdFontArchive.licenseEntry],\n { maxBuffer: 1_000_000, windowsHide: true },\n );\n } catch (error) {\n throw new Error(\"Could not extract Hack Nerd Font from its archive.\", {\n cause: error,\n });\n }\n\n await saveAndRegisterFont(\n localAppData,\n NERD_FONT_FAMILY,\n \"pimpt-hack-nerd-font-v3.5.1.ttf\",\n \"pimpt-hack-nerd-font-LICENSE.md\",\n fontData,\n licenseData,\n );\n } finally {\n await rm(temporaryDirectory, { recursive: true, force: true });\n }\n}\n","import { execFileSync } from \"node:child_process\";\n\nconst terminalIconsVersion = \"0.11.0\";\nconst psReadLineVersion = \"2.4.5\";\n\nfunction runPowerShell(script: string, operation: string): void {\n if (process.platform !== \"win32\") {\n throw new Error(`${operation} is only supported on Windows.`);\n }\n\n try {\n execFileSync(\n \"powershell.exe\",\n [\n \"-NoLogo\",\n \"-NoProfile\",\n \"-NonInteractive\",\n \"-Command\",\n script,\n ],\n { encoding: \"utf8\", windowsHide: true, stdio: \"pipe\" },\n );\n } catch (error) {\n throw new Error(`${operation} failed: ${String(error)}`, { cause: error });\n }\n}\n\nfunction installPowerShellGalleryModule(\n moduleName: \"Terminal-Icons\" | \"PSReadLine\",\n version: string,\n allowClobber: boolean,\n): void {\n const clobberOption = allowClobber ? \"-AllowClobber \" : \"\";\n const script = String.raw`$ErrorActionPreference = 'Stop'\n$protocols = [Net.ServicePointManager]::SecurityProtocol -bor [Net.SecurityProtocolType]::Tls12\n[Net.ServicePointManager]::SecurityProtocol = $protocols\n$nugetProvider = Get-PackageProvider -Name NuGet -ListAvailable -ErrorAction SilentlyContinue\nif (-not $nugetProvider) {\n Install-PackageProvider -Name NuGet -MinimumVersion '2.8.5.201' -Scope CurrentUser -Force -Confirm:$false -ErrorAction Stop | Out-Null\n}\n\n$requiredVersion = [version]'${version}'\n$module = Get-Module -ListAvailable -Name '${moduleName}' | Where-Object { $_.Version -eq $requiredVersion }\nif (-not $module) {\n Install-Module -Name '${moduleName}' -RequiredVersion '${version}' -Scope CurrentUser -Repository PSGallery ${clobberOption}-Force -Confirm:$false -ErrorAction Stop\n}\n\n$module = Get-Module -ListAvailable -Name '${moduleName}' | Where-Object { $_.Version -eq $requiredVersion }\nif (-not $module) {\n throw '${moduleName} ${version} is not available after installation.'\n}`;\n runPowerShell(script, `Installing the ${moduleName} PowerShell module`);\n}\n\nfunction addPowerShellProfileBlock(\n feature:\n | \"terminal icons\"\n | \"command history preview\"\n | \"tree-style ls\"\n | \"tree-style ls alias\"\n | \"tree-style ls v2\",\n commands: string[],\n operation: string,\n): void {\n const beginMarker = `# >>> pimpt ${feature} >>>`;\n const endMarker = `# <<< pimpt ${feature} <<<`;\n const block = [beginMarker, ...commands, endMarker].join(\"\\r\\n\");\n const encodedMarker = Buffer.from(beginMarker, \"utf16le\").toString(\"base64\");\n const encodedBlock = Buffer.from(block, \"utf16le\").toString(\"base64\");\n const script = String.raw`$ErrorActionPreference = 'Stop'\n$profilePath = $PROFILE.CurrentUserCurrentHost\n$profileDirectory = Split-Path -Parent $profilePath\nif (-not (Test-Path -LiteralPath $profileDirectory)) {\n New-Item -ItemType Directory -Path $profileDirectory -Force | Out-Null\n}\n\n$profileContent = ''\nif (Test-Path -LiteralPath $profilePath) {\n $profileContent = Get-Content -LiteralPath $profilePath -Raw\n}\n\n$beginMarker = [System.Text.Encoding]::Unicode.GetString([Convert]::FromBase64String('${encodedMarker}'))\nif ($profileContent -notmatch [regex]::Escape($beginMarker)) {\n if (-not (Test-Path -LiteralPath $profilePath)) {\n New-Item -ItemType File -Path $profilePath -Force | Out-Null\n }\n\n $encoding = 'Default'\n $bytes = [System.IO.File]::ReadAllBytes($profilePath)\n if ($bytes.Length -ge 2 -and $bytes[0] -eq 0xFF -and $bytes[1] -eq 0xFE) {\n $encoding = 'Unicode'\n } elseif ($bytes.Length -ge 2 -and $bytes[0] -eq 0xFE -and $bytes[1] -eq 0xFF) {\n $encoding = 'BigEndianUnicode'\n } elseif ($bytes.Length -ge 3 -and $bytes[0] -eq 0xEF -and $bytes[1] -eq 0xBB -and $bytes[2] -eq 0xBF) {\n $encoding = 'UTF8'\n }\n\n $profileBlock = [System.Text.Encoding]::Unicode.GetString([Convert]::FromBase64String('${encodedBlock}'))\n $newline = [Environment]::NewLine\n $separator = if ($profileContent.Length -gt 0 -and -not $profileContent.EndsWith([string][char]10)) { $newline } else { '' }\n Add-Content -LiteralPath $profilePath -Encoding $encoding -Value \"$separator$profileBlock\"\n}`;\n runPowerShell(script, operation);\n}\n\nexport function installTerminalIconsModule(): void {\n installPowerShellGalleryModule(\n \"Terminal-Icons\",\n terminalIconsVersion,\n false,\n );\n}\n\nexport function installPSReadLineModule(): void {\n installPowerShellGalleryModule(\"PSReadLine\", psReadLineVersion, true);\n}\n\nexport function addTerminalIconsToPowerShellProfile(): void {\n addPowerShellProfileBlock(\n \"terminal icons\",\n [\"Import-Module Terminal-Icons -ErrorAction Stop\"],\n \"Adding Terminal-Icons to the Windows PowerShell profile\",\n );\n}\n\nexport function addHistoryPreviewToPowerShellProfile(): void {\n addPowerShellProfileBlock(\n \"command history preview\",\n [\n `Import-Module PSReadLine -RequiredVersion '${psReadLineVersion}' -Force -ErrorAction Stop`,\n \"Set-PSReadLineOption -PredictionSource History -PredictionViewStyle ListView\",\n ],\n \"Adding command history preview to the Windows PowerShell profile\",\n );\n}\n\nexport interface PowerShellProfileFeatures {\n terminalIcons: boolean;\n historyPreview: boolean;\n treeListing: boolean;\n}\n\nexport function readPowerShellProfileFeatures(): PowerShellProfileFeatures {\n const features: PowerShellProfileFeatures = {\n terminalIcons: false,\n historyPreview: false,\n treeListing: false,\n };\n if (process.platform !== \"win32\") return features;\n\n let encodedProfile: string;\n try {\n encodedProfile = execFileSync(\n \"powershell.exe\",\n [\n \"-NoLogo\",\n \"-NoProfile\",\n \"-NonInteractive\",\n \"-Command\",\n String.raw`$profilePath = $PROFILE.CurrentUserCurrentHost\nif (Test-Path -LiteralPath $profilePath) {\n $content = [System.IO.File]::ReadAllText($profilePath)\n [Console]::Out.Write([Convert]::ToBase64String([System.Text.Encoding]::Unicode.GetBytes($content)))\n}`,\n ],\n { encoding: \"utf8\", windowsHide: true, stdio: \"pipe\" },\n ).trim();\n } catch (error) {\n throw new Error(\"Could not inspect the Windows PowerShell profile.\", {\n cause: error,\n });\n }\n\n const profile = Buffer.from(encodedProfile, \"base64\").toString(\"utf16le\");\n const hasBlock = (name: string) =>\n profile.includes(`# >>> pimpt ${name} >>>`) &&\n profile.includes(`# <<< pimpt ${name} <<<`);\n\n features.terminalIcons = hasBlock(\"terminal icons\");\n features.historyPreview = hasBlock(\"command history preview\");\n features.treeListing =\n hasBlock(\"tree-style ls v2\") || hasBlock(\"tree-style ls\");\n return features;\n}\n\nexport function addTreeListingToPowerShellProfile(): void {\n addPowerShellProfileBlock(\n \"tree-style ls alias\",\n [\"Remove-Item Alias:ls -Force -ErrorAction SilentlyContinue\"],\n \"Enabling the tree-style ls command in the Windows PowerShell profile\",\n );\n addPowerShellProfileBlock(\n \"tree-style ls v2\",\n [\n \"function ls {\",\n \" [CmdletBinding()]\",\n \" param(\",\n \" [Parameter(Position = 0)] [string]$Path = '.',\",\n \" [ValidateRange(1, 32)] [int]$Depth = 4,\",\n \" [ValidateRange(1, 10000)] [int]$Limit = 50,\",\n \" [switch]$All,\",\n \" [switch]$Force\",\n \" )\",\n \" try {\",\n \" $root = Get-Item -LiteralPath $Path -ErrorAction Stop\",\n \" } catch {\",\n \" Write-Host (\\\"ls: cannot access '{0}': {1}\\\" -f $Path, $_.Exception.Message) -ForegroundColor Red\",\n \" return\",\n \" }\",\n \" if (-not $root.PSIsContainer) {\",\n \" Write-Host $root.Name -ForegroundColor Gray\",\n \" return\",\n \" }\",\n \" Write-Host $root.FullName -ForegroundColor Cyan\",\n \" $state = [pscustomobject]@{ Shown = 0; Limit = $Limit; All = [bool]$All; Truncated = $false }\",\n \" $walk = {\",\n \" param($Directory, [string]$Prefix, [int]$CurrentDepth, $State)\",\n \" if ($CurrentDepth -ge $Depth) { return }\",\n \" try {\",\n \" $children = @(Get-ChildItem -LiteralPath $Directory.FullName -Force:$Force -ErrorAction Stop | Sort-Object @{ Expression = { if ($_.PSIsContainer) { 0 } else { 1 } } }, Name)\",\n \" } catch {\",\n \" Write-Host (\\\"{0}└── [cannot read: {1}]\\\" -f $Prefix, $_.Exception.Message) -ForegroundColor Red\",\n \" return\",\n \" }\",\n \" for ($index = 0; $index -lt $children.Count; $index++) {\",\n \" if (-not $State.All -and $State.Shown -ge $State.Limit) {\",\n \" $State.Truncated = $true\",\n \" break\",\n \" }\",\n \" $entry = $children[$index]\",\n \" $isLast = $index -eq ($children.Count - 1)\",\n \" $connector = if ($isLast) { '└── ' } else { '├── ' }\",\n \" $color = if ($entry.PSIsContainer) { 'Cyan' } else { 'Gray' }\",\n \" Write-Host ($Prefix + $connector + $entry.Name) -ForegroundColor $color\",\n \" $State.Shown++\",\n \" if ($entry.PSIsContainer -and ($CurrentDepth + 1 -lt $Depth)) {\",\n \" $childPrefix = $Prefix + $(if ($isLast) { ' ' } else { '│ ' })\",\n \" & $walk $entry $childPrefix ($CurrentDepth + 1) $State\",\n \" if ($State.Truncated) { break }\",\n \" }\",\n \" }\",\n \" }\",\n \" & $walk $root '' 0 $state\",\n \" if ($state.Truncated) {\",\n \" Write-Host (\\\"… output capped at {0} entries (use -Limit <number> or -All)\\\" -f $state.Limit) -ForegroundColor DarkGray\",\n \" }\",\n \"}\",\n ],\n \"Adding the tree-style ls command to the Windows PowerShell profile\",\n );\n}\n","import { settings, type SettingValue } from \"./settings.js\";\n\nexport interface SummarySection {\n group: string;\n rows: [string, string][];\n}\n\nexport function normalizeHex(value: string): string {\n return value.trim().replace(/^#?/, \"#\").toUpperCase();\n}\n\nexport function buildSummarySections(\n answers: Record<string, SettingValue>,\n): SummarySection[] {\n const sections: SummarySection[] = [];\n let current: SummarySection | null = null;\n\n for (const setting of settings) {\n const value = answers[setting.id];\n if (value === undefined) continue;\n\n if (!current || current.group !== setting.group) {\n current = { group: setting.group, rows: [] };\n sections.push(current);\n }\n\n current.rows.push([setting.label, setting.summarize(value)]);\n }\n\n return sections;\n}\n","import {\n copyFileSync,\n existsSync,\n lstatSync,\n readFileSync,\n readdirSync,\n writeFileSync,\n} from \"node:fs\";\nimport { basename, dirname, join } from \"node:path\";\nimport { applyEdits, modify, parse, type ParseError } from \"jsonc-parser\";\n\nexport interface SettingsBackup {\n path: string;\n createdAt: Date;\n}\n\nexport class InvalidSettingsFileError extends Error {\n constructor() {\n super(\n \"Windows Terminal settings.json is invalid JSONC. No changes were written. Restore the file from a backup before trying again.\",\n );\n this.name = \"InvalidSettingsFileError\";\n }\n}\n\n/**\n * Sucht die Windows Terminal settings.json.\n * Prüft Stable, Preview und Canary in dieser Reihenfolge.\n */\nexport function findSettingsPath(): string | undefined {\n const localAppData = process.env.LOCALAPPDATA;\n if (!localAppData) return undefined;\n\n const candidates = [\n join(localAppData, \"Packages\", \"Microsoft.WindowsTerminal_8wekyb3d8bbwe\", \"LocalState\", \"settings.json\"),\n join(localAppData, \"Packages\", \"Microsoft.WindowsTerminalPreview_8wekyb3d8bbwe\", \"LocalState\", \"settings.json\"),\n join(localAppData, \"Packages\", \"Microsoft.WindowsTerminal.Canary_8wekyb3d8bbwe\", \"LocalState\", \"settings.json\"),\n ];\n\n for (const path of candidates) {\n if (existsSync(path)) return path;\n }\n\n return undefined;\n}\n\n/**\n * Liest die settings.json als rohen Text.\n */\nexport function readSettingsFile(settingsPath: string): string {\n return readFileSync(settingsPath, \"utf8\");\n}\n\n/**\n * Schreibt die geänderte settings.json zurück. Kommentare und Formatierung\n * werden so weit wie möglich erhalten (jsonc-parser.modify).\n */\nexport function writeSettingsFile(settingsPath: string, content: string): void {\n writeFileSync(settingsPath, content, \"utf8\");\n}\n\nexport function createSettingsBackup(settingsPath: string): string {\n const timestamp = Date.now();\n const backupPrefix = `${basename(settingsPath)}.backup-${timestamp}-`;\n let sequence = 0;\n let backupPath: string;\n\n do {\n backupPath = join(dirname(settingsPath), `${backupPrefix}${sequence}`);\n sequence += 1;\n } while (existsSync(backupPath));\n\n copyFileSync(settingsPath, backupPath);\n return backupPath;\n}\n\nexport function listSettingsBackups(settingsPath: string): SettingsBackup[] {\n const backupPrefix = `${basename(settingsPath)}.backup-`;\n\n return readdirSync(dirname(settingsPath))\n .filter((name) => name.startsWith(backupPrefix))\n .flatMap((name): SettingsBackup[] => {\n const match = /^(\\d+)-(\\d+)$/.exec(name.slice(backupPrefix.length));\n if (!match) return [];\n\n const path = join(dirname(settingsPath), name);\n if (!lstatSync(path).isFile()) return [];\n\n return [{ path, createdAt: new Date(Number(match[1])) }];\n })\n .sort((left, right) => right.createdAt.getTime() - left.createdAt.getTime());\n}\n\nexport function restoreSettingsBackup(\n settingsPath: string,\n backupPath: string,\n): string {\n const backup = listSettingsBackups(settingsPath).find(\n (candidate) => candidate.path === backupPath,\n );\n if (!backup) {\n throw new Error(\"The selected settings backup is not available.\");\n }\n\n const content = readFileSync(backup.path, \"utf8\");\n const parseErrors: ParseError[] = [];\n const parsedContent = parse(content, parseErrors, { allowTrailingComma: true });\n if (\n parseErrors.length > 0 ||\n parsedContent === null ||\n typeof parsedContent !== \"object\" ||\n Array.isArray(parsedContent)\n ) {\n throw new Error(\"The selected backup is invalid JSONC. Nothing was changed.\");\n }\n\n const safetyBackupPath = createSettingsBackup(settingsPath);\n writeSettingsFile(settingsPath, content);\n return safetyBackupPath;\n}\n\n/**\n * Wendet eine Änderung an der settings.json an.\n *\n * @param content - Der aktuelle Inhalt der settings.json\n * @param jsonPath - Pfad im JSON, z. B. [\"profiles\", \"defaults\", \"background\"]\n * @param value - Der neue Wert\n * @returns Der neu geschriebene Dateiinhalt\n */\nexport function setSetting(\n content: string,\n jsonPath: (string | number)[],\n value: unknown,\n): string {\n const parseErrors: ParseError[] = [];\n const parsedContent = parse(content, parseErrors, { allowTrailingComma: true });\n if (\n parseErrors.length > 0 ||\n parsedContent === null ||\n typeof parsedContent !== \"object\" ||\n Array.isArray(parsedContent)\n ) {\n throw new InvalidSettingsFileError();\n }\n\n const edits = modify(content, jsonPath, value, {\n formattingOptions: {\n tabSize: 4,\n insertSpaces: true,\n },\n });\n return applyEdits(content, edits);\n}\n"],"mappings":"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","names":["readFileSync","pc","parse","execFileSync","join","parse","setting","readFileSync","pc"]}
package/package.json CHANGED
@@ -1,13 +1,14 @@
1
1
  {
2
2
  "name": "@m0x373/pimpt",
3
- "version": "0.1.0",
3
+ "version": "0.1.2",
4
4
  "description": "Interactive setup assistant for Windows Terminal",
5
5
  "type": "module",
6
6
  "bin": {
7
7
  "pimpt": "dist/index.js"
8
8
  },
9
9
  "files": [
10
- "dist"
10
+ "dist",
11
+ "README.md"
11
12
  ],
12
13
  "scripts": {
13
14
  "build": "tsup src/index.ts --format esm --clean --sourcemap",