Skip to content

Commit cae158c

Browse files
liangmiQwQfengmk2
andauthored
fix(cli): use jsonc-parser for vscode settings (#1003)
Close #1002 Use `jsonc-parser` as underlying parser for vscode setting migration. This approach is temporary because it won't keep comments in the file. Now it is added in `dependencies`, I am not sure whether `devDependencies` is better in this project. --------- Co-authored-by: MK (fengmk2) <fengmk2@gmail.com>
1 parent c2b1c15 commit cae158c

5 files changed

Lines changed: 62 additions & 3 deletions

File tree

packages/cli/package.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -339,6 +339,7 @@
339339
"detect-indent": "catalog:",
340340
"detect-newline": "catalog:",
341341
"glob": "catalog:",
342+
"jsonc-parser": "catalog:",
342343
"lint-staged": "catalog:",
343344
"minimatch": "catalog:",
344345
"mri": "catalog:",

packages/cli/src/utils/__tests__/editor.spec.ts

Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,48 @@ describe('writeEditorConfigs', () => {
4040
expect(settings['editor.formatOnSave']).toBe(true);
4141
});
4242

43+
it('merges existing vscode JSONC settings (comments, trailing commas)', async () => {
44+
const projectRoot = createTempDir();
45+
46+
const vscodeDir = path.join(projectRoot, '.vscode');
47+
fs.mkdirSync(vscodeDir, { recursive: true });
48+
fs.writeFileSync(
49+
path.join(vscodeDir, 'settings.json'),
50+
`{
51+
// JSONC comment
52+
"editor.formatOnSave": false,
53+
"editor.codeActionsOnSave": {
54+
// preserve existing key
55+
"source.organizeImports": "explicit",
56+
},
57+
}
58+
`,
59+
'utf8',
60+
);
61+
62+
await writeEditorConfigs({
63+
projectRoot,
64+
editorId: 'vscode',
65+
interactive: false,
66+
silent: true,
67+
});
68+
69+
const settings = JSON.parse(
70+
fs.readFileSync(path.join(projectRoot, '.vscode', 'settings.json'), 'utf8'),
71+
) as Record<string, unknown>;
72+
73+
// Existing key is preserved (merge never overwrites)
74+
expect(settings['editor.formatOnSave']).toBe(false);
75+
76+
// New keys are added
77+
expect(settings['editor.defaultFormatter']).toBe('oxc.oxc-vscode');
78+
expect(settings['oxc.fmt.configPath']).toBe('./vite.config.ts');
79+
80+
const codeActions = settings['editor.codeActionsOnSave'] as Record<string, unknown>;
81+
expect(codeActions['source.organizeImports']).toBe('explicit');
82+
expect(codeActions['source.fixAll.oxc']).toBe('explicit');
83+
});
84+
4385
it('writes zed settings that align formatter config with vite.config.ts', async () => {
4486
const projectRoot = createTempDir();
4587

packages/cli/src/utils/editor.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -340,7 +340,7 @@ function mergeAndWriteEditorConfig(
340340
displayPath: string,
341341
silent = false,
342342
) {
343-
const existing = readJsonFile(filePath);
343+
const existing = readJsonFile(filePath, true);
344344
const merged = mergeEditorConfigs(existing, incoming, fileName);
345345
writeJsonFile(filePath, merged);
346346
if (!silent) {

packages/cli/src/utils/json.ts

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,10 +2,15 @@ import fs from 'node:fs';
22

33
import detectIndent from 'detect-indent';
44
import { detectNewline } from 'detect-newline';
5+
import { parse as parseJsonc } from 'jsonc-parser';
56

6-
export function readJsonFile<T = Record<string, unknown>>(file: string): T {
7+
export function readJsonFile<T = Record<string, unknown>>(
8+
file: string,
9+
allowComments?: boolean,
10+
): T {
711
const content = fs.readFileSync(file, 'utf-8');
8-
return JSON.parse(content) as T;
12+
const parseFunction = allowComments ? parseJsonc : JSON.parse;
13+
return parseFunction(content) as T;
914
}
1015

1116
export function writeJsonFile<T = Record<string, unknown>>(file: string, data: T) {

pnpm-lock.yaml

Lines changed: 11 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)