skir-codemirror-plugin 1.0.2 → 1.0.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (42) hide show
  1. package/README.md +15 -6
  2. package/dist/codemirror/create_editor_state.d.ts +4 -2
  3. package/dist/codemirror/create_editor_state.d.ts.map +1 -1
  4. package/dist/codemirror/create_editor_state.js +178 -31
  5. package/dist/codemirror/create_editor_state.js.map +1 -1
  6. package/dist/codemirror/json_linter.d.ts.map +1 -1
  7. package/dist/codemirror/json_linter.js +67 -3
  8. package/dist/codemirror/json_linter.js.map +1 -1
  9. package/dist/codemirror/json_state.d.ts +5 -1
  10. package/dist/codemirror/json_state.d.ts.map +1 -1
  11. package/dist/codemirror/json_state.js +26 -1
  12. package/dist/codemirror/json_state.js.map +1 -1
  13. package/dist/index.d.ts +1 -1
  14. package/dist/index.d.ts.map +1 -1
  15. package/dist/index.js.map +1 -1
  16. package/dist/json/json_parser.js +35 -1
  17. package/dist/json/json_parser.js.map +1 -1
  18. package/dist/json/json_parser.test.js +48 -0
  19. package/dist/json/json_parser.test.js.map +1 -1
  20. package/dist/json/schema_validator.d.ts.map +1 -1
  21. package/dist/json/schema_validator.js +16 -11
  22. package/dist/json/schema_validator.js.map +1 -1
  23. package/dist/json/schema_validator.test.js +71 -0
  24. package/dist/json/schema_validator.test.js.map +1 -1
  25. package/dist/json/to_json.d.ts +1 -1
  26. package/dist/json/to_json.d.ts.map +1 -1
  27. package/dist/json/to_json.js +3 -3
  28. package/dist/json/to_json.js.map +1 -1
  29. package/dist/json/types.d.ts +4 -0
  30. package/dist/json/types.d.ts.map +1 -1
  31. package/dist/json/types.js.map +1 -1
  32. package/package.json +2 -3
  33. package/src/codemirror/create_editor_state.ts +272 -31
  34. package/src/codemirror/json_linter.ts +89 -4
  35. package/src/codemirror/json_state.ts +44 -1
  36. package/src/index.ts +1 -0
  37. package/src/json/json_parser.test.ts +51 -0
  38. package/src/json/json_parser.ts +37 -1
  39. package/src/json/schema_validator.test.ts +75 -0
  40. package/src/json/schema_validator.ts +20 -10
  41. package/src/json/to_json.ts +3 -3
  42. package/src/json/types.ts +7 -0
@@ -1 +1 @@
1
- {"version":3,"file":"json_linter.js","sourceRoot":"","sources":["../../src/codemirror/json_linter.ts"],"names":[],"mappings":"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","sourcesContent":["import { Diagnostic } from \"@codemirror/lint\";\nimport { EditorView } from \"@codemirror/view\";\nimport { Hint, JsonError, JsonLiteral, TypeHint } from \"../json/types\";\nimport { ensureJsonState, jsonStateField } from \"./json_state\";\n\nexport function jsonLinter(\n editable: \"editable\" | \"read-only\",\n): (view: EditorView) => Diagnostic[] {\n function lintJson(view: EditorView): Diagnostic[] {\n const jsonState = view.state.field(jsonStateField, false);\n if (!jsonState) {\n return [];\n }\n\n const parseResult = jsonState.parseResult;\n if (parseResult.errors.length) {\n return parseResult.errors.map(errorToDiagnostic);\n }\n\n if (!jsonState.validationResult) {\n return [];\n }\n\n const { errors, hints } = jsonState.validationResult;\n return errors\n .map(errorToDiagnostic)\n .concat(hints.map((hint) => hintToDiagnostic(hint, editable)));\n }\n\n return lintJson;\n}\n\nfunction errorToDiagnostic(error: JsonError): Diagnostic {\n return {\n from: error.segment.start,\n to: error.segment.end,\n message: error.message,\n severity: \"error\",\n renderMessage: (): Node => {\n const wrapper = document.createElement(\"div\");\n wrapper.className = \"cm-diagnostic-wrapper\";\n wrapper.textContent = error.message;\n return wrapper;\n },\n };\n}\n\nfunction getStringControlRows(\n view: EditorView,\n typeHint: TypeHint,\n value: JsonLiteral,\n editable: \"editable\" | \"read-only\",\n): HTMLDivElement[] {\n const headerRow = document.createElement(\"div\");\n headerRow.textContent = typeHint.message as string;\n\n const jsonCode = value.jsonCode;\n const parsedValue = JSON.parse(jsonCode) as string;\n\n const controlsRow = document.createElement(\"div\");\n controlsRow.className = \"cm-diagnostic-controls\";\n\n const label = document.createElement(\"span\");\n // label.className = \"cm-diagnostic-label\";\n label.textContent = \"Value:\";\n\n const textarea = document.createElement(\"textarea\");\n textarea.className = \"cm-diagnostic-textarea\";\n textarea.value = parsedValue;\n textarea.rows = 1;\n const isReadOnly = editable === \"read-only\";\n textarea.readOnly = isReadOnly;\n\n textarea.addEventListener(\"keydown\", (e) => {\n if (e.key === \"Enter\" && !e.shiftKey && !isReadOnly) {\n e.preventDefault();\n const newValue = textarea.value;\n const newJsonString = JSON.stringify(newValue);\n\n view.dispatch({\n changes: {\n from: typeHint.segment.start,\n to: typeHint.segment.end,\n insert: newJsonString,\n },\n });\n }\n });\n\n controlsRow.appendChild(label);\n controlsRow.appendChild(textarea);\n\n return [headerRow, controlsRow];\n}\n\nfunction getTimestampControlRows(\n view: EditorView,\n typeHint: TypeHint,\n): HTMLDivElement[] {\n const headerRow = document.createElement(\"div\");\n headerRow.textContent = typeHint.message as string;\n\n let unixMillis: number | undefined;\n {\n const value = typeHint.valueContext!.value;\n if (value.kind === \"object\") {\n const unixMillisKv = value.keyValues[\"unix_millis\"];\n if (\n unixMillisKv &&\n unixMillisKv.value.kind === \"literal\" &&\n unixMillisKv.value.type === \"number\"\n ) {\n unixMillis = JSON.parse(unixMillisKv.value.jsonCode) as number;\n if (unixMillis < -8640000000000000 || 8640000000000000 < unixMillis) {\n unixMillis = undefined;\n }\n }\n }\n }\n\n // Row 1: unix_millis input\n const row1 = document.createElement(\"div\");\n row1.className = \"cm-diagnostic-controls\";\n\n const label1 = document.createElement(\"span\");\n label1.className = \"cm-diagnostic-label\";\n label1.textContent = \"unix_millis:\";\n\n const field1 = document.createElement(\"div\");\n field1.className = \"cm-timestamp-field\";\n\n const unixMillisInput = document.createElement(\"input\");\n unixMillisInput.type = \"text\";\n unixMillisInput.className = \"cm-diagnostic-input\";\n unixMillisInput.value = unixMillis !== undefined ? String(unixMillis) : \"\";\n\n const error1 = document.createElement(\"div\");\n error1.className = \"cm-diagnostic-error-message\";\n error1.style.display = \"none\";\n\n field1.appendChild(unixMillisInput);\n field1.appendChild(error1);\n row1.appendChild(label1);\n row1.appendChild(field1);\n\n // Row 2: ISO 8601 date string input\n const row2 = document.createElement(\"div\");\n row2.className = \"cm-diagnostic-controls\";\n\n const label2 = document.createElement(\"span\");\n label2.className = \"cm-diagnostic-label\";\n label2.textContent = \"ISO 8601:\";\n\n const field2 = document.createElement(\"div\");\n field2.className = \"cm-timestamp-field\";\n\n const isoInput = document.createElement(\"input\");\n isoInput.type = \"text\";\n isoInput.className = \"cm-diagnostic-input\";\n if (unixMillis !== undefined) {\n isoInput.value = new Date(unixMillis).toISOString();\n }\n\n const error2 = document.createElement(\"div\");\n error2.className = \"cm-diagnostic-error-message\";\n error2.style.display = \"none\";\n\n field2.appendChild(isoInput);\n field2.appendChild(error2);\n row2.appendChild(label2);\n row2.appendChild(field2);\n\n // Row 3: Now button\n const row3 = document.createElement(\"div\");\n row3.className = \"cm-diagnostic-controls\";\n\n const nowButton = document.createElement(\"button\");\n nowButton.className = \"cm-diagnostic-button\";\n nowButton.textContent = \"Now\";\n\n row3.appendChild(nowButton);\n\n // Helper function to update the editor\n const updateEditor = (millis: number, formatted: string): void => {\n const value = typeHint.valueContext!.value;\n\n // Check if both keys exist in the object\n if (value.kind === \"object\") {\n const unixMillisKv = value.keyValues[\"unix_millis\"];\n const formattedKv = value.keyValues[\"formatted\"];\n\n if (unixMillisKv && formattedKv) {\n // Update both values individually\n view.dispatch({\n changes: [\n {\n from: unixMillisKv.value.segment.start,\n to: unixMillisKv.value.segment.end,\n insert: String(millis),\n },\n {\n from: formattedKv.value.segment.start,\n to: formattedKv.value.segment.end,\n insert: JSON.stringify(formatted),\n },\n ],\n });\n\n return;\n }\n }\n\n // Default behavior: replace the whole object\n const newJsonString = `{\"unix_millis\": ${millis}, \"formatted\": \"${formatted}\"}`;\n\n const segment = typeHint.valueContext!.value.segment;\n view.dispatch({\n changes: {\n from: segment.start,\n to: segment.end,\n insert: newJsonString,\n },\n });\n\n ensureJsonState(view, (view as any).schema);\n };\n\n // Enter key handler for unix_millis input\n unixMillisInput.addEventListener(\"keydown\", (e) => {\n if (e.key === \"Enter\") {\n e.preventDefault();\n const value = unixMillisInput.value.trim();\n const millis = Number(value);\n\n // Validate\n if (value === \"\" || isNaN(millis) || !Number.isInteger(millis)) {\n error1.textContent = \"Must be an integer\";\n error1.style.display = \"block\";\n return;\n }\n\n if (millis < -8640000000000000 || millis > 8640000000000000) {\n error1.textContent = \"Timestamp out of range\";\n error1.style.display = \"block\";\n return;\n }\n\n error1.style.display = \"none\";\n error2.style.display = \"none\";\n\n // Update ISO field and editor\n const formatted = new Date(millis).toISOString();\n isoInput.value = formatted;\n updateEditor(millis, formatted);\n }\n });\n\n // Enter key handler for ISO 8601 input\n isoInput.addEventListener(\"keydown\", (e) => {\n if (e.key === \"Enter\") {\n e.preventDefault();\n const value = isoInput.value.trim();\n const millis = Date.parse(value);\n\n // Validate\n if (isNaN(millis)) {\n error2.textContent = \"Invalid ISO 8601 date string\";\n error2.style.display = \"block\";\n return;\n }\n\n error1.style.display = \"none\";\n error2.style.display = \"none\";\n\n // Update unix_millis field and editor\n const formatted = new Date(millis).toISOString();\n unixMillisInput.value = String(millis);\n updateEditor(millis, formatted);\n }\n });\n\n // Now button handler\n nowButton.addEventListener(\"click\", () => {\n const now = Date.now();\n const formatted = new Date(now).toISOString();\n\n unixMillisInput.value = String(now);\n isoInput.value = formatted;\n error1.style.display = \"none\";\n error2.style.display = \"none\";\n\n updateEditor(now, formatted);\n });\n\n const controlsRow = document.createElement(\"div\");\n controlsRow.appendChild(row1);\n controlsRow.appendChild(row2);\n controlsRow.appendChild(row3);\n\n return [headerRow, controlsRow];\n}\n\nfunction hintToDiagnostic(\n typeHint: Hint,\n editable: \"editable\" | \"read-only\",\n): Diagnostic {\n const { message } = typeHint;\n return {\n from: typeHint.segment.start,\n to: typeHint.segment.end,\n message: \"\",\n severity: \"info\",\n renderMessage: (view): Node => {\n const wrapper = document.createElement(\"div\");\n wrapper.className = \"cm-diagnostic-wrapper\";\n\n let rows: HTMLDivElement[];\n if (\n (message === \"string\" || message === \"string?\") &&\n typeHint.valueContext &&\n typeHint.valueContext.value.kind === \"literal\" &&\n typeHint.valueContext.value.type === \"string\"\n ) {\n // Render a string editing control for string hints.\n rows = getStringControlRows(\n view,\n typeHint,\n typeHint.valueContext.value,\n editable,\n );\n } else if (\n (message === \"timestamp\" || message === \"timestamp?\") &&\n typeHint.valueContext &&\n typeHint.valueContext.value.kind === \"object\" &&\n editable === \"editable\"\n ) {\n // Render a timestamp editing control for timestamp hints.\n rows = getTimestampControlRows(view, typeHint);\n } else {\n // Display the message for non-string types\n const pieces = typeof message === \"string\" ? [message] : message;\n rows = pieces.map((piece) => {\n const row = document.createElement(\"div\");\n row.textContent = piece;\n return row;\n });\n }\n\n for (const row of rows) {\n row.classList.add(\"diagnostic-row\");\n wrapper.appendChild(row);\n }\n\n return wrapper;\n },\n markClass: \"\",\n };\n}\n"]}
1
+ {"version":3,"file":"json_linter.js","sourceRoot":"","sources":["../../src/codemirror/json_linter.ts"],"names":[],"mappings":"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","sourcesContent":["import { Diagnostic } from \"@codemirror/lint\";\nimport { EditorView } from \"@codemirror/view\";\nimport { makeJsonTemplate } from \"../json/to_json\";\nimport { Hint, JsonError, JsonLiteral, TypeHint } from \"../json/types\";\nimport { jsonStateField } from \"./json_state\";\n\nexport function jsonLinter(\n editable: \"editable\" | \"read-only\",\n): (view: EditorView) => Diagnostic[] {\n function lintJson(view: EditorView): Diagnostic[] {\n const jsonState = view.state.field(jsonStateField, false);\n if (!jsonState) {\n return [];\n }\n\n const parseResult = jsonState.parseResult;\n if (parseResult.errors.length) {\n return parseResult.errors.map(errorToDiagnostic);\n }\n\n if (!jsonState.validationResult) {\n return [];\n }\n\n const { errors, hints } = jsonState.validationResult;\n return errors\n .map(errorToDiagnostic)\n .concat(hints.map((hint) => hintToDiagnostic(hint, editable)));\n }\n\n return lintJson;\n}\n\nfunction errorToDiagnostic(error: JsonError): Diagnostic {\n return {\n from: error.segment.start,\n to: error.segment.end,\n message: error.message,\n severity: \"error\",\n renderMessage: (): Node => {\n const wrapper = document.createElement(\"div\");\n wrapper.className = \"cm-diagnostic-wrapper\";\n wrapper.textContent = error.message;\n return wrapper;\n },\n };\n}\n\nfunction getStringControlRows(\n view: EditorView,\n typeHint: TypeHint,\n value: JsonLiteral,\n editable: \"editable\" | \"read-only\",\n): HTMLDivElement[] {\n const headerRow = document.createElement(\"div\");\n headerRow.textContent = typeHint.message as string;\n\n const jsonCode = value.jsonCode;\n const parsedValue = JSON.parse(jsonCode) as string;\n\n const controlsRow = document.createElement(\"div\");\n controlsRow.className = \"cm-diagnostic-controls\";\n\n const label = document.createElement(\"span\");\n // label.className = \"cm-diagnostic-label\";\n label.textContent = \"Value:\";\n\n const textarea = document.createElement(\"textarea\");\n textarea.className = \"cm-diagnostic-textarea\";\n textarea.value = parsedValue;\n textarea.rows = 1;\n const isReadOnly = editable === \"read-only\";\n textarea.readOnly = isReadOnly;\n\n textarea.addEventListener(\"keydown\", (e) => {\n if (e.key === \"Enter\" && !e.shiftKey && !isReadOnly) {\n e.preventDefault();\n const newValue = textarea.value;\n const newJsonString = JSON.stringify(newValue);\n\n view.dispatch({\n changes: {\n from: typeHint.segment.start,\n to: typeHint.segment.end,\n insert: newJsonString,\n },\n });\n }\n });\n\n controlsRow.appendChild(label);\n controlsRow.appendChild(textarea);\n\n return [headerRow, controlsRow];\n}\n\nfunction getTimestampControlRows(\n view: EditorView,\n typeHint: TypeHint,\n): HTMLDivElement[] {\n const headerRow = document.createElement(\"div\");\n headerRow.textContent = typeHint.message as string;\n\n let unixMillis: number | undefined;\n {\n const value = typeHint.valueContext!.value;\n if (value.kind === \"object\") {\n const unixMillisKv = value.keyValues[\"unix_millis\"];\n if (\n unixMillisKv &&\n unixMillisKv.value.kind === \"literal\" &&\n unixMillisKv.value.type === \"number\"\n ) {\n unixMillis = JSON.parse(unixMillisKv.value.jsonCode) as number;\n if (unixMillis < -8640000000000000 || 8640000000000000 < unixMillis) {\n unixMillis = undefined;\n }\n }\n }\n }\n\n // Row 1: unix_millis input\n const row1 = document.createElement(\"div\");\n row1.className = \"cm-diagnostic-controls\";\n\n const label1 = document.createElement(\"span\");\n label1.className = \"cm-diagnostic-label\";\n label1.textContent = \"unix_millis:\";\n\n const field1 = document.createElement(\"div\");\n field1.className = \"cm-timestamp-field\";\n\n const unixMillisInput = document.createElement(\"input\");\n unixMillisInput.type = \"text\";\n unixMillisInput.className = \"cm-diagnostic-input\";\n unixMillisInput.value = unixMillis !== undefined ? String(unixMillis) : \"\";\n\n const error1 = document.createElement(\"div\");\n error1.className = \"cm-diagnostic-error-message\";\n error1.style.display = \"none\";\n\n field1.appendChild(unixMillisInput);\n field1.appendChild(error1);\n row1.appendChild(label1);\n row1.appendChild(field1);\n\n // Row 2: ISO 8601 date string input\n const row2 = document.createElement(\"div\");\n row2.className = \"cm-diagnostic-controls\";\n\n const label2 = document.createElement(\"span\");\n label2.className = \"cm-diagnostic-label\";\n label2.textContent = \"ISO 8601:\";\n\n const field2 = document.createElement(\"div\");\n field2.className = \"cm-timestamp-field\";\n\n const isoInput = document.createElement(\"input\");\n isoInput.type = \"text\";\n isoInput.className = \"cm-diagnostic-input\";\n if (unixMillis !== undefined) {\n isoInput.value = new Date(unixMillis).toISOString();\n }\n\n const error2 = document.createElement(\"div\");\n error2.className = \"cm-diagnostic-error-message\";\n error2.style.display = \"none\";\n\n field2.appendChild(isoInput);\n field2.appendChild(error2);\n row2.appendChild(label2);\n row2.appendChild(field2);\n\n // Row 3: Now button\n const row3 = document.createElement(\"div\");\n row3.className = \"cm-diagnostic-controls\";\n\n const nowButton = document.createElement(\"button\");\n nowButton.className = \"cm-diagnostic-button\";\n nowButton.textContent = \"Now\";\n\n row3.appendChild(nowButton);\n\n // Helper function to update the editor\n const updateEditor = (millis: number, formatted: string): void => {\n const value = typeHint.valueContext!.value;\n\n // Check if both keys exist in the object\n if (value.kind === \"object\") {\n const unixMillisKv = value.keyValues[\"unix_millis\"];\n const formattedKv = value.keyValues[\"formatted\"];\n\n if (unixMillisKv && formattedKv) {\n // Update both values individually\n view.dispatch({\n changes: [\n {\n from: unixMillisKv.value.segment.start,\n to: unixMillisKv.value.segment.end,\n insert: String(millis),\n },\n {\n from: formattedKv.value.segment.start,\n to: formattedKv.value.segment.end,\n insert: JSON.stringify(formatted),\n },\n ],\n });\n\n return;\n }\n }\n\n // Default behavior: replace the whole object\n const newJsonString = `{\"unix_millis\": ${millis}, \"formatted\": \"${formatted}\"}`;\n\n const segment = typeHint.valueContext!.value.segment;\n view.dispatch({\n changes: {\n from: segment.start,\n to: segment.end,\n insert: newJsonString,\n },\n });\n };\n\n // Enter key handler for unix_millis input\n unixMillisInput.addEventListener(\"keydown\", (e) => {\n if (e.key === \"Enter\") {\n e.preventDefault();\n const value = unixMillisInput.value.trim();\n const millis = Number(value);\n\n // Validate\n if (value === \"\" || isNaN(millis) || !Number.isInteger(millis)) {\n error1.textContent = \"Must be an integer\";\n error1.style.display = \"block\";\n return;\n }\n\n if (millis < -8640000000000000 || millis > 8640000000000000) {\n error1.textContent = \"Timestamp out of range\";\n error1.style.display = \"block\";\n return;\n }\n\n error1.style.display = \"none\";\n error2.style.display = \"none\";\n\n // Update ISO field and editor\n const formatted = new Date(millis).toISOString();\n isoInput.value = formatted;\n updateEditor(millis, formatted);\n }\n });\n\n // Enter key handler for ISO 8601 input\n isoInput.addEventListener(\"keydown\", (e) => {\n if (e.key === \"Enter\") {\n e.preventDefault();\n const value = isoInput.value.trim();\n const millis = Date.parse(value);\n\n // Validate\n if (isNaN(millis)) {\n error2.textContent = \"Invalid ISO 8601 date string\";\n error2.style.display = \"block\";\n return;\n }\n\n error1.style.display = \"none\";\n error2.style.display = \"none\";\n\n // Update unix_millis field and editor\n const formatted = new Date(millis).toISOString();\n unixMillisInput.value = String(millis);\n updateEditor(millis, formatted);\n }\n });\n\n // Now button handler\n nowButton.addEventListener(\"click\", () => {\n const now = Date.now();\n const formatted = new Date(now).toISOString();\n\n unixMillisInput.value = String(now);\n isoInput.value = formatted;\n error1.style.display = \"none\";\n error2.style.display = \"none\";\n\n updateEditor(now, formatted);\n });\n\n const controlsRow = document.createElement(\"div\");\n controlsRow.appendChild(row1);\n controlsRow.appendChild(row2);\n controlsRow.appendChild(row3);\n\n return [headerRow, controlsRow];\n}\n\nfunction getEnumDropdown(\n view: EditorView,\n typeHint: TypeHint,\n enumDefinition: NonNullable<TypeHint[\"enumDefinition\"]>,\n): HTMLDivElement {\n const controlsRow = document.createElement(\"div\");\n controlsRow.className = \"cm-diagnostic-controls\";\n\n const label = document.createElement(\"span\");\n label.className = \"cm-diagnostic-label\";\n label.textContent = \"Variant:\";\n\n const select = document.createElement(\"select\");\n select.className = \"cm-diagnostic-input\";\n\n {\n // Add the UNKNOWN variant\n const option = document.createElement(\"option\");\n option.value = \"UNKNOWN\";\n option.textContent = \"UNKNOWN\";\n select.appendChild(option);\n }\n for (const variant of enumDefinition.variants) {\n const option = document.createElement(\"option\");\n option.value = variant.name;\n option.textContent = variant.name;\n select.appendChild(option);\n }\n\n const currentValue = typeHint.valueContext?.value;\n if (\n currentValue &&\n currentValue.kind === \"literal\" &&\n currentValue.type === \"string\"\n ) {\n try {\n select.value = JSON.parse(currentValue.jsonCode) as string;\n } catch {\n // Ignore invalid value and keep the default selection.\n }\n }\n\n select.addEventListener(\"change\", () => {\n const variant = enumDefinition.variants.find(\n (variant) => variant.name === select.value,\n )!;\n let newJsonString: string;\n if (variant.type) {\n const jsonState = view.state.field(jsonStateField, false)!;\n const valueJson = makeJsonTemplate(\n variant.type,\n jsonState.recordIdToDefinition,\n );\n newJsonString = JSON.stringify(\n {\n kind: variant.name,\n value: valueJson,\n },\n null,\n 2,\n ).replaceAll(\"\\n\", \"\\n\" + \" \".repeat(typeHint.valueContext.value.indent));\n } else {\n newJsonString = JSON.stringify(variant.name);\n }\n view.dispatch({\n changes: {\n from: typeHint.segment.start,\n to: typeHint.segment.end,\n insert: newJsonString,\n },\n });\n });\n\n controlsRow.appendChild(label);\n controlsRow.appendChild(select);\n return controlsRow;\n}\n\nfunction hintToDiagnostic(\n typeHint: Hint,\n editable: \"editable\" | \"read-only\",\n): Diagnostic {\n const { message } = typeHint;\n return {\n from: typeHint.segment.start,\n to: typeHint.segment.end,\n message: \"\",\n severity: \"info\",\n renderMessage: (view): Node => {\n const wrapper = document.createElement(\"div\");\n wrapper.className = \"cm-diagnostic-wrapper\";\n\n let rows: HTMLDivElement[];\n if (\n (message === \"string\" || message === \"string?\") &&\n typeHint.valueContext &&\n typeHint.valueContext.value.kind === \"literal\" &&\n typeHint.valueContext.value.type === \"string\"\n ) {\n // Render a string editing control for string hints.\n rows = getStringControlRows(\n view,\n typeHint,\n typeHint.valueContext.value,\n editable,\n );\n } else if (\n (message === \"timestamp\" || message === \"timestamp?\") &&\n typeHint.valueContext &&\n typeHint.valueContext.value.kind === \"object\" &&\n editable === \"editable\"\n ) {\n // Render a timestamp editing control for timestamp hints.\n rows = getTimestampControlRows(view, typeHint);\n } else {\n // Display the message.\n const pieces = typeof message === \"string\" ? [message] : message;\n rows = pieces.map((piece) => {\n const row = document.createElement(\"div\");\n row.textContent = piece;\n return row;\n });\n if (\n typeHint.valueContext &&\n typeHint.enumDefinition &&\n editable === \"editable\"\n ) {\n // Render a dropdown for selecting a different variant.\n rows.push(getEnumDropdown(view, typeHint, typeHint.enumDefinition));\n }\n }\n\n for (const row of rows) {\n row.classList.add(\"diagnostic-row\");\n wrapper.appendChild(row);\n }\n\n return wrapper;\n },\n markClass: \"\",\n };\n}\n"]}
@@ -1,10 +1,14 @@
1
1
  import { Extension, StateField } from "@codemirror/state";
2
2
  import { EditorView } from "@codemirror/view";
3
- import type { JsonParseResult, TypeDefinition, ValidationResult } from "../json/types";
3
+ import type { JsonParseResult, RecordDefinition, TypeDefinition, ValidationResult } from "../json/types";
4
4
  export interface JsonState {
5
5
  readonly parseResult: JsonParseResult;
6
6
  readonly validationResult?: ValidationResult;
7
7
  readonly source: string;
8
+ readonly schema: TypeDefinition;
9
+ readonly recordIdToDefinition: {
10
+ [id: string]: RecordDefinition;
11
+ };
8
12
  }
9
13
  export declare const jsonStateField: StateField<JsonState | null>;
10
14
  /**
@@ -1 +1 @@
1
- {"version":3,"file":"json_state.d.ts","sourceRoot":"","sources":["../../src/codemirror/json_state.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,SAAS,EAET,UAAU,EAEX,MAAM,mBAAmB,CAAC;AAC3B,OAAO,EAAE,UAAU,EAA0B,MAAM,kBAAkB,CAAC;AAGtE,OAAO,KAAK,EACV,eAAe,EACf,cAAc,EACd,gBAAgB,EACjB,MAAM,eAAe,CAAC;AAEvB,MAAM,WAAW,SAAS;IACxB,QAAQ,CAAC,WAAW,EAAE,eAAe,CAAC;IACtC,QAAQ,CAAC,gBAAgB,CAAC,EAAE,gBAAgB,CAAC;IAC7C,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;CACzB;AAID,eAAO,MAAM,cAAc,8BAYzB,CAAC;AAEH;;;GAGG;AACH,wBAAgB,eAAe,CAC7B,IAAI,EAAE,UAAU,EAChB,MAAM,EAAE,cAAc,GACrB,SAAS,CA0BX;AAED,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,cAAc,GAAG,SAAS,EAAE,CAiGvE"}
1
+ {"version":3,"file":"json_state.d.ts","sourceRoot":"","sources":["../../src/codemirror/json_state.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,SAAS,EAET,UAAU,EAEX,MAAM,mBAAmB,CAAC;AAC3B,OAAO,EAAE,UAAU,EAA0B,MAAM,kBAAkB,CAAC;AAGtE,OAAO,KAAK,EACV,eAAe,EACf,gBAAgB,EAChB,cAAc,EACd,gBAAgB,EACjB,MAAM,eAAe,CAAC;AAEvB,MAAM,WAAW,SAAS;IACxB,QAAQ,CAAC,WAAW,EAAE,eAAe,CAAC;IACtC,QAAQ,CAAC,gBAAgB,CAAC,EAAE,gBAAgB,CAAC;IAC7C,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,MAAM,EAAE,cAAc,CAAC;IAChC,QAAQ,CAAC,oBAAoB,EAAE;QAAE,CAAC,EAAE,EAAE,MAAM,GAAG,gBAAgB,CAAA;KAAE,CAAC;CACnE;AAID,eAAO,MAAM,cAAc,8BAYzB,CAAC;AAEH;;;GAGG;AACH,wBAAgB,eAAe,CAC7B,IAAI,EAAE,UAAU,EAChB,MAAM,EAAE,cAAc,GACrB,SAAS,CAkCX;AAED,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,cAAc,GAAG,SAAS,EAAE,CAiHvE"}
@@ -33,7 +33,14 @@ export function ensureJsonState(view, schema) {
33
33
  if (parseResult.value) {
34
34
  validationResult = validateSchema(parseResult.value, schema);
35
35
  }
36
- const newState = { parseResult, validationResult, source };
36
+ const recordIdToDefinition = indexRecordDefinitions(schema, currentState);
37
+ const newState = {
38
+ parseResult,
39
+ validationResult,
40
+ source,
41
+ schema,
42
+ recordIdToDefinition,
43
+ };
37
44
  // Update the state if it's different
38
45
  if (!currentState || currentState !== newState) {
39
46
  view.dispatch({
@@ -93,22 +100,30 @@ export function debouncedJsonParser(schema) {
93
100
  to: edit.segment.end,
94
101
  insert: edit.replacement,
95
102
  }));
103
+ const oldState = this.view.state.field(jsonStateField, false);
104
+ const recordIdToDefinition = indexRecordDefinitions(schema, oldState);
96
105
  this.view.dispatch({
97
106
  changes,
98
107
  effects: updateJsonState.of({
99
108
  parseResult,
100
109
  validationResult,
101
110
  source,
111
+ schema,
112
+ recordIdToDefinition,
102
113
  }),
103
114
  scrollIntoView: true,
104
115
  });
105
116
  }
106
117
  else {
118
+ const oldState = this.view.state.field(jsonStateField, false);
119
+ const recordIdToDefinition = indexRecordDefinitions(schema, oldState);
107
120
  this.view.dispatch({
108
121
  effects: updateJsonState.of({
109
122
  parseResult,
110
123
  validationResult,
111
124
  source,
125
+ schema,
126
+ recordIdToDefinition,
112
127
  }),
113
128
  });
114
129
  }
@@ -121,4 +136,14 @@ export function debouncedJsonParser(schema) {
121
136
  }),
122
137
  ];
123
138
  }
139
+ function indexRecordDefinitions(schema, oldState) {
140
+ if (schema === oldState?.schema) {
141
+ return oldState.recordIdToDefinition;
142
+ }
143
+ const idToRecordDef = {};
144
+ for (const recordDef of schema.records) {
145
+ idToRecordDef[recordDef.id] = recordDef;
146
+ }
147
+ return idToRecordDef;
148
+ }
124
149
  //# sourceMappingURL=json_state.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"json_state.js","sourceRoot":"","sources":["../../src/codemirror/json_state.ts"],"names":[],"mappings":"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","sourcesContent":["import {\n Extension,\n StateEffect,\n StateField,\n Transaction,\n} from \"@codemirror/state\";\nimport { EditorView, ViewPlugin, ViewUpdate } from \"@codemirror/view\";\nimport { parseJsonValue } from \"../json/json_parser\";\nimport { validateSchema } from \"../json/schema_validator\";\nimport type {\n JsonParseResult,\n TypeDefinition,\n ValidationResult,\n} from \"../json/types\";\n\nexport interface JsonState {\n readonly parseResult: JsonParseResult;\n readonly validationResult?: ValidationResult;\n readonly source: string;\n}\n\nconst updateJsonState = StateEffect.define<JsonState>();\n\nexport const jsonStateField = StateField.define<JsonState | null>({\n create(): JsonState | null {\n return null;\n },\n update(value, tr): JsonState | null {\n for (const effect of tr.effects) {\n if (effect.is(updateJsonState)) {\n return effect.value;\n }\n }\n return value;\n },\n});\n\n/**\n * Ensures the JSON state is up-to-date with the current document.\n * If the state is stale or missing, triggers an immediate parse and returns the updated state.\n */\nexport function ensureJsonState(\n view: EditorView,\n schema: TypeDefinition,\n): JsonState {\n const currentState = view.state.field(jsonStateField, false);\n const source = view.state.doc.toString();\n\n // If the source hasn't changed, return the current state\n if (currentState && currentState.source === source) {\n return currentState;\n }\n\n // Parse and validate immediately\n const parseResult = parseJsonValue(source);\n let validationResult: ValidationResult | undefined;\n if (parseResult.value) {\n validationResult = validateSchema(parseResult.value, schema);\n }\n\n const newState: JsonState = { parseResult, validationResult, source };\n\n // Update the state if it's different\n if (!currentState || currentState !== newState) {\n view.dispatch({\n effects: updateJsonState.of(newState),\n });\n }\n\n return newState;\n}\n\nexport function debouncedJsonParser(schema: TypeDefinition): Extension[] {\n return [\n jsonStateField,\n ViewPlugin.fromClass(\n class {\n timeout: number | null = null;\n view: EditorView;\n\n constructor(view: EditorView) {\n this.view = view;\n this.scheduleUpdate();\n }\n\n update(update: ViewUpdate): void {\n if (update.docChanged) {\n const isUndo = update.transactions.some(\n (tr) =>\n tr.annotation(Transaction.userEvent) === \"undo\" ||\n tr.annotation(Transaction.userEvent) === \"redo\",\n );\n this.scheduleUpdate(isUndo ? \"from-undo\" : undefined);\n }\n }\n\n scheduleUpdate(fromUndo?: \"from-undo\"): void {\n if (this.timeout !== null) {\n clearTimeout(this.timeout);\n }\n this.timeout = window.setTimeout(() => {\n this.parseJson(fromUndo);\n this.timeout = null;\n }, 200);\n }\n\n parseJson(fromUndo: \"from-undo\" | undefined): void {\n const source = this.view.state.doc.toString();\n const parseResult = parseJsonValue(source);\n\n let validationResult: ValidationResult | undefined;\n if (parseResult.value) {\n validationResult = validateSchema(parseResult.value, schema);\n }\n\n const cursorInsideEdit = (): boolean => {\n const cursorPos = this.view.state.selection.main.head;\n return parseResult.edits.some(\n (edit) =>\n edit.segment.start <= cursorPos &&\n cursorPos <= edit.segment.end,\n );\n };\n\n // Apply edits if all these conditions are satisfied:\n // - no error\n // - the cursor is not inside any of the edited segments, to avoid\n // disrupting the user while they're typing\n // - the update is not triggered by an undo operation\n if (\n !fromUndo &&\n parseResult.edits.length &&\n parseResult.errors.length <= 0 &&\n !cursorInsideEdit()\n ) {\n const changes = parseResult.edits.map((edit) => ({\n from: edit.segment.start,\n to: edit.segment.end,\n insert: edit.replacement,\n }));\n\n this.view.dispatch({\n changes,\n effects: updateJsonState.of({\n parseResult,\n validationResult,\n source,\n }),\n scrollIntoView: true,\n });\n } else {\n this.view.dispatch({\n effects: updateJsonState.of({\n parseResult,\n validationResult,\n source,\n }),\n });\n }\n }\n\n destroy(): void {\n if (this.timeout !== null) {\n clearTimeout(this.timeout);\n }\n }\n },\n ),\n ];\n}\n"]}
1
+ {"version":3,"file":"json_state.js","sourceRoot":"","sources":["../../src/codemirror/json_state.ts"],"names":[],"mappings":"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","sourcesContent":["import {\n Extension,\n StateEffect,\n StateField,\n Transaction,\n} from \"@codemirror/state\";\nimport { EditorView, ViewPlugin, ViewUpdate } from \"@codemirror/view\";\nimport { parseJsonValue } from \"../json/json_parser\";\nimport { validateSchema } from \"../json/schema_validator\";\nimport type {\n JsonParseResult,\n RecordDefinition,\n TypeDefinition,\n ValidationResult,\n} from \"../json/types\";\n\nexport interface JsonState {\n readonly parseResult: JsonParseResult;\n readonly validationResult?: ValidationResult;\n readonly source: string;\n readonly schema: TypeDefinition;\n readonly recordIdToDefinition: { [id: string]: RecordDefinition };\n}\n\nconst updateJsonState = StateEffect.define<JsonState>();\n\nexport const jsonStateField = StateField.define<JsonState | null>({\n create(): JsonState | null {\n return null;\n },\n update(value, tr): JsonState | null {\n for (const effect of tr.effects) {\n if (effect.is(updateJsonState)) {\n return effect.value;\n }\n }\n return value;\n },\n});\n\n/**\n * Ensures the JSON state is up-to-date with the current document.\n * If the state is stale or missing, triggers an immediate parse and returns the updated state.\n */\nexport function ensureJsonState(\n view: EditorView,\n schema: TypeDefinition,\n): JsonState {\n const currentState = view.state.field(jsonStateField, false);\n const source = view.state.doc.toString();\n\n // If the source hasn't changed, return the current state\n if (currentState && currentState.source === source) {\n return currentState;\n }\n\n // Parse and validate immediately\n const parseResult = parseJsonValue(source);\n let validationResult: ValidationResult | undefined;\n if (parseResult.value) {\n validationResult = validateSchema(parseResult.value, schema);\n }\n\n const recordIdToDefinition = indexRecordDefinitions(schema, currentState);\n\n const newState: JsonState = {\n parseResult,\n validationResult,\n source,\n schema,\n recordIdToDefinition,\n };\n\n // Update the state if it's different\n if (!currentState || currentState !== newState) {\n view.dispatch({\n effects: updateJsonState.of(newState),\n });\n }\n\n return newState;\n}\n\nexport function debouncedJsonParser(schema: TypeDefinition): Extension[] {\n return [\n jsonStateField,\n ViewPlugin.fromClass(\n class {\n timeout: number | null = null;\n view: EditorView;\n\n constructor(view: EditorView) {\n this.view = view;\n this.scheduleUpdate();\n }\n\n update(update: ViewUpdate): void {\n if (update.docChanged) {\n const isUndo = update.transactions.some(\n (tr) =>\n tr.annotation(Transaction.userEvent) === \"undo\" ||\n tr.annotation(Transaction.userEvent) === \"redo\",\n );\n this.scheduleUpdate(isUndo ? \"from-undo\" : undefined);\n }\n }\n\n scheduleUpdate(fromUndo?: \"from-undo\"): void {\n if (this.timeout !== null) {\n clearTimeout(this.timeout);\n }\n this.timeout = window.setTimeout(() => {\n this.parseJson(fromUndo);\n this.timeout = null;\n }, 200);\n }\n\n parseJson(fromUndo: \"from-undo\" | undefined): void {\n const source = this.view.state.doc.toString();\n const parseResult = parseJsonValue(source);\n\n let validationResult: ValidationResult | undefined;\n if (parseResult.value) {\n validationResult = validateSchema(parseResult.value, schema);\n }\n\n const cursorInsideEdit = (): boolean => {\n const cursorPos = this.view.state.selection.main.head;\n return parseResult.edits.some(\n (edit) =>\n edit.segment.start <= cursorPos &&\n cursorPos <= edit.segment.end,\n );\n };\n\n // Apply edits if all these conditions are satisfied:\n // - no error\n // - the cursor is not inside any of the edited segments, to avoid\n // disrupting the user while they're typing\n // - the update is not triggered by an undo operation\n if (\n !fromUndo &&\n parseResult.edits.length &&\n parseResult.errors.length <= 0 &&\n !cursorInsideEdit()\n ) {\n const changes = parseResult.edits.map((edit) => ({\n from: edit.segment.start,\n to: edit.segment.end,\n insert: edit.replacement,\n }));\n\n const oldState = this.view.state.field(jsonStateField, false);\n const recordIdToDefinition = indexRecordDefinitions(\n schema,\n oldState,\n );\n\n this.view.dispatch({\n changes,\n effects: updateJsonState.of({\n parseResult,\n validationResult,\n source,\n schema,\n recordIdToDefinition,\n }),\n scrollIntoView: true,\n });\n } else {\n const oldState = this.view.state.field(jsonStateField, false);\n const recordIdToDefinition = indexRecordDefinitions(\n schema,\n oldState,\n );\n\n this.view.dispatch({\n effects: updateJsonState.of({\n parseResult,\n validationResult,\n source,\n schema,\n recordIdToDefinition,\n }),\n });\n }\n }\n\n destroy(): void {\n if (this.timeout !== null) {\n clearTimeout(this.timeout);\n }\n }\n },\n ),\n ];\n}\n\nfunction indexRecordDefinitions(\n schema: TypeDefinition,\n oldState: JsonState | null | undefined,\n): {\n [id: string]: RecordDefinition;\n} {\n if (schema === oldState?.schema) {\n return oldState.recordIdToDefinition;\n }\n const idToRecordDef: { [id: string]: RecordDefinition } = {};\n for (const recordDef of schema.records) {\n idToRecordDef[recordDef.id] = recordDef;\n }\n return idToRecordDef;\n}\n"]}
package/dist/index.d.ts CHANGED
@@ -1,5 +1,5 @@
1
1
  export { createEditorState } from "./codemirror/create_editor_state";
2
- export type { CreateEditorStateParams, CustomTheme, } from "./codemirror/create_editor_state";
2
+ export type { BuiltinThemeName, CreateEditorStateParams, CustomTheme, } from "./codemirror/create_editor_state";
3
3
  export { ensureJsonState } from "./codemirror/json_state";
4
4
  export type { JsonState } from "./codemirror/json_state";
5
5
  export { toJson } from "./json/to_json";
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,iBAAiB,EAAE,MAAM,kCAAkC,CAAC;AACrE,YAAY,EACV,uBAAuB,EACvB,WAAW,GACZ,MAAM,kCAAkC,CAAC;AAC1C,OAAO,EAAE,eAAe,EAAE,MAAM,yBAAyB,CAAC;AAC1D,YAAY,EAAE,SAAS,EAAE,MAAM,yBAAyB,CAAC;AACzD,OAAO,EAAE,MAAM,EAAE,MAAM,gBAAgB,CAAC;AACxC,mBAAmB,cAAc,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,iBAAiB,EAAE,MAAM,kCAAkC,CAAC;AACrE,YAAY,EACV,gBAAgB,EAChB,uBAAuB,EACvB,WAAW,GACZ,MAAM,kCAAkC,CAAC;AAC1C,OAAO,EAAE,eAAe,EAAE,MAAM,yBAAyB,CAAC;AAC1D,YAAY,EAAE,SAAS,EAAE,MAAM,yBAAyB,CAAC;AACzD,OAAO,EAAE,MAAM,EAAE,MAAM,gBAAgB,CAAC;AACxC,mBAAmB,cAAc,CAAC"}
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,iBAAiB,EAAE,MAAM,kCAAkC,CAAC;AAKrE,OAAO,EAAE,eAAe,EAAE,MAAM,yBAAyB,CAAC;AAE1D,OAAO,EAAE,MAAM,EAAE,MAAM,gBAAgB,CAAC","sourcesContent":["export { createEditorState } from \"./codemirror/create_editor_state\";\nexport type {\n CreateEditorStateParams,\n CustomTheme,\n} from \"./codemirror/create_editor_state\";\nexport { ensureJsonState } from \"./codemirror/json_state\";\nexport type { JsonState } from \"./codemirror/json_state\";\nexport { toJson } from \"./json/to_json\";\nexport type * from \"./json/types\";\n"]}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,iBAAiB,EAAE,MAAM,kCAAkC,CAAC;AAMrE,OAAO,EAAE,eAAe,EAAE,MAAM,yBAAyB,CAAC;AAE1D,OAAO,EAAE,MAAM,EAAE,MAAM,gBAAgB,CAAC","sourcesContent":["export { createEditorState } from \"./codemirror/create_editor_state\";\nexport type {\n BuiltinThemeName,\n CreateEditorStateParams,\n CustomTheme,\n} from \"./codemirror/create_editor_state\";\nexport { ensureJsonState } from \"./codemirror/json_state\";\nexport type { JsonState } from \"./codemirror/json_state\";\nexport { toJson } from \"./json/to_json\";\nexport type * from \"./json/types\";\n"]}
@@ -19,12 +19,25 @@ export function parseJsonValue(input) {
19
19
  function tokenize(input) {
20
20
  const tokens = [];
21
21
  let pos = 0;
22
+ let lineIndent = 0;
23
+ let lineHasContent = false;
22
24
  const whitespaceRegex = /[ \t\r\n]*/y;
23
25
  const tokenRegex = /([[\]{}:,]|(-?(?:0|[1-9]\d*)(?:\.\d+)?(?:[eE][+-]?\d+)?)|false|true|null|("(((?=\\)\\(["\\/ bfnrt]|u[0-9a-fA-F]{4}))|[^"\\\0-\x1F\x7F]+)*")|$)/y;
24
26
  while (true) {
27
+ const beforeWhitespacePos = pos;
25
28
  whitespaceRegex.lastIndex = pos;
26
29
  whitespaceRegex.exec(input);
27
30
  pos = whitespaceRegex.lastIndex;
31
+ for (let i = beforeWhitespacePos; i < pos; ++i) {
32
+ const ch = input[i];
33
+ if (ch === "\n") {
34
+ lineIndent = 0;
35
+ lineHasContent = false;
36
+ }
37
+ else if (!lineHasContent && (ch === " " || ch === "\t")) {
38
+ lineIndent++;
39
+ }
40
+ }
28
41
  tokenRegex.lastIndex = pos;
29
42
  const tokenMatch = tokenRegex.exec(input);
30
43
  if (tokenMatch) {
@@ -33,9 +46,16 @@ function tokenize(input) {
33
46
  start: pos,
34
47
  end: pos + tokenText.length,
35
48
  };
36
- const token = { segment, jsonCode: tokenText };
49
+ const token = {
50
+ segment,
51
+ jsonCode: tokenText,
52
+ indent: lineIndent,
53
+ };
37
54
  pos = tokenRegex.lastIndex;
38
55
  tokens.push(token);
56
+ if (tokenText !== "") {
57
+ lineHasContent = true;
58
+ }
39
59
  if (tokenText === "") {
40
60
  return {
41
61
  kind: "tokens",
@@ -69,6 +89,7 @@ class JsonParser {
69
89
  parseValueOrSkip() {
70
90
  const token = this.peekToken();
71
91
  const firstChar = token.jsonCode ? token.jsonCode[0] : "";
92
+ const { indent } = token;
72
93
  switch (firstChar) {
73
94
  case "[":
74
95
  return this.parseArray();
@@ -82,6 +103,7 @@ class JsonParser {
82
103
  segment: token.segment,
83
104
  jsonCode: "null",
84
105
  type: "null",
106
+ indent,
85
107
  };
86
108
  case "f":
87
109
  this.nextToken();
@@ -91,6 +113,7 @@ class JsonParser {
91
113
  segment: token.segment,
92
114
  jsonCode: "false",
93
115
  type: "boolean",
116
+ indent,
94
117
  };
95
118
  case "t":
96
119
  this.nextToken();
@@ -100,6 +123,7 @@ class JsonParser {
100
123
  segment: token.segment,
101
124
  jsonCode: "true",
102
125
  type: "boolean",
126
+ indent,
103
127
  };
104
128
  case '"':
105
129
  this.nextToken();
@@ -109,6 +133,7 @@ class JsonParser {
109
133
  segment: token.segment,
110
134
  jsonCode: token.jsonCode,
111
135
  type: "string",
136
+ indent,
112
137
  };
113
138
  case "0":
114
139
  case "1":
@@ -128,6 +153,7 @@ class JsonParser {
128
153
  segment: token.segment,
129
154
  jsonCode: token.jsonCode,
130
155
  type: "number",
156
+ indent,
131
157
  };
132
158
  }
133
159
  this.errors.push({
@@ -140,6 +166,7 @@ class JsonParser {
140
166
  }
141
167
  parseArray() {
142
168
  const leftBracket = this.nextToken();
169
+ const { indent } = leftBracket;
143
170
  const values = [];
144
171
  while (true) {
145
172
  if (this.peekToken().jsonCode === "]") {
@@ -152,6 +179,7 @@ class JsonParser {
152
179
  end: rightBracket.segment.end,
153
180
  },
154
181
  values,
182
+ indent,
155
183
  };
156
184
  }
157
185
  if (this.peekToken().jsonCode === "}") {
@@ -169,6 +197,7 @@ class JsonParser {
169
197
  end: wrongBracket.segment.end,
170
198
  },
171
199
  values,
200
+ indent,
172
201
  };
173
202
  }
174
203
  if (this.peekToken().jsonCode === "") {
@@ -182,6 +211,7 @@ class JsonParser {
182
211
  end: this.peekToken().segment.start,
183
212
  },
184
213
  values,
214
+ indent,
185
215
  };
186
216
  }
187
217
  const value = this.parseValueOrSkip();
@@ -203,6 +233,7 @@ class JsonParser {
203
233
  }
204
234
  parseObject() {
205
235
  const leftBracket = this.nextToken();
236
+ const { indent } = leftBracket;
206
237
  const keyValues = {};
207
238
  const allKeys = [];
208
239
  while (true) {
@@ -217,6 +248,7 @@ class JsonParser {
217
248
  },
218
249
  keyValues,
219
250
  allKeys,
251
+ indent,
220
252
  };
221
253
  }
222
254
  if (this.peekToken().jsonCode === "]") {
@@ -235,6 +267,7 @@ class JsonParser {
235
267
  },
236
268
  keyValues,
237
269
  allKeys,
270
+ indent,
238
271
  };
239
272
  }
240
273
  if (this.peekToken().jsonCode === "") {
@@ -249,6 +282,7 @@ class JsonParser {
249
282
  },
250
283
  keyValues,
251
284
  allKeys,
285
+ indent,
252
286
  };
253
287
  }
254
288
  const keyToken = this.peekToken();
@@ -1 +1 @@
1
- {"version":3,"file":"json_parser.js","sourceRoot":"","sources":["../../src/json/json_parser.ts"],"names":[],"mappings":"AAYA,MAAM,UAAU,cAAc,CAAC,KAAa;IAC1C,MAAM,MAAM,GAAG,QAAQ,CAAC,KAAK,CAAC,CAAC;IAC/B,IAAI,MAAM,CAAC,IAAI,KAAK,OAAO,EAAE,CAAC;QAC5B,OAAO;YACL,KAAK,EAAE,SAAS;YAChB,MAAM,EAAE,CAAC,MAAM,CAAC;YAChB,KAAK,EAAE,EAAE;SACV,CAAC;IACJ,CAAC;IACD,MAAM,MAAM,GAAG,IAAI,UAAU,CAAC,MAAM,CAAC,MAAM,EAAE,KAAK,CAAC,CAAC;IACpD,MAAM,WAAW,GAAG,MAAM,CAAC,gBAAgB,EAAE,CAAC;IAC9C,MAAM,CAAC,SAAS,EAAE,CAAC;IAEnB,OAAO;QACL,KAAK,EAAE,WAAW;QAClB,MAAM,EAAE,MAAM,CAAC,MAAM;QACrB,KAAK,EAAE,MAAM,CAAC,KAAK;KACpB,CAAC;AACJ,CAAC;AAYD,SAAS,QAAQ,CAAC,KAAa;IAC7B,MAAM,MAAM,GAAgB,EAAE,CAAC;IAC/B,IAAI,GAAG,GAAG,CAAC,CAAC;IAEZ,MAAM,eAAe,GAAG,aAAa,CAAC;IACtC,MAAM,UAAU,GACd,iJAAiJ,CAAC;IAEpJ,OAAO,IAAI,EAAE,CAAC;QACZ,eAAe,CAAC,SAAS,GAAG,GAAG,CAAC;QAChC,eAAe,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QAC5B,GAAG,GAAG,eAAe,CAAC,SAAS,CAAC;QAEhC,UAAU,CAAC,SAAS,GAAG,GAAG,CAAC;QAC3B,MAAM,UAAU,GAAG,UAAU,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QAC1C,IAAI,UAAU,EAAE,CAAC;YACf,MAAM,SAAS,GAAG,UAAU,CAAC,CAAC,CAAC,CAAC;YAChC,MAAM,OAAO,GAAY;gBACvB,KAAK,EAAE,GAAG;gBACV,GAAG,EAAE,GAAG,GAAG,SAAS,CAAC,MAAM;aAC5B,CAAC;YACF,MAAM,KAAK,GAAc,EAAE,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,CAAC;YAC1D,GAAG,GAAG,UAAU,CAAC,SAAS,CAAC;YAC3B,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;YACnB,IAAI,SAAS,KAAK,EAAE,EAAE,CAAC;gBACrB,OAAO;oBACL,IAAI,EAAE,QAAQ;oBACd,MAAM,EAAE,MAAM;iBACf,CAAC;YACJ,CAAC;QACH,CAAC;aAAM,CAAC;YACN,oDAAoD;YACpD,MAAM,iBAAiB,GAAG,OAAO,CAAC;YAClC,iBAAiB,CAAC,SAAS,GAAG,GAAG,GAAG,CAAC,CAAC;YACtC,iBAAiB,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;YAC9B,MAAM,GAAG,GAAG,iBAAiB,CAAC,SAAS,IAAI,GAAG,GAAG,CAAC,CAAC;YACnD,OAAO;gBACL,IAAI,EAAE,OAAO;gBACb,OAAO,EAAE,aAAa;gBACtB,OAAO,EAAE,EAAE,KAAK,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE;aAClC,CAAC;QACJ,CAAC;IACH,CAAC;AACH,CAAC;AAED,MAAM,UAAU;IACd,YAAoB,MAAmB,EAAmB,KAAa;QAAnD,WAAM,GAAN,MAAM,CAAa;QAAmB,UAAK,GAAL,KAAK,CAAQ;QAC/D,eAAU,GAAG,CAAC,CAAC;QACvB,WAAM,GAAgB,EAAE,CAAC;QACzB,UAAK,GAAe,EAAE,CAAC;QACf,WAAM,GAAG,EAAE,CAAC;IAJsD,CAAC;IAM3E,gBAAgB;QACd,MAAM,KAAK,GAAG,IAAI,CAAC,SAAS,EAAE,CAAC;QAC/B,MAAM,SAAS,GAAG,KAAK,CAAC,QAAQ,CAAC,CAAC,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;QAE1D,QAAQ,SAAS,EAAE,CAAC;YAClB,KAAK,GAAG;gBACN,OAAO,IAAI,CAAC,UAAU,EAAE,CAAC;YAC3B,KAAK,GAAG;gBACN,OAAO,IAAI,CAAC,WAAW,EAAE,CAAC;YAC5B,KAAK,GAAG;gBACN,IAAI,CAAC,SAAS,EAAE,CAAC;gBACjB,OAAO;oBACL,IAAI,EAAE,SAAS;oBACf,UAAU,EAAE,KAAK,CAAC,OAAO;oBACzB,OAAO,EAAE,KAAK,CAAC,OAAO;oBACtB,QAAQ,EAAE,MAAM;oBAChB,IAAI,EAAE,MAAM;iBACb,CAAC;YACJ,KAAK,GAAG;gBACN,IAAI,CAAC,SAAS,EAAE,CAAC;gBACjB,OAAO;oBACL,IAAI,EAAE,SAAS;oBACf,UAAU,EAAE,KAAK,CAAC,OAAO;oBACzB,OAAO,EAAE,KAAK,CAAC,OAAO;oBACtB,QAAQ,EAAE,OAAO;oBACjB,IAAI,EAAE,SAAS;iBAChB,CAAC;YACJ,KAAK,GAAG;gBACN,IAAI,CAAC,SAAS,EAAE,CAAC;gBACjB,OAAO;oBACL,IAAI,EAAE,SAAS;oBACf,UAAU,EAAE,KAAK,CAAC,OAAO;oBACzB,OAAO,EAAE,KAAK,CAAC,OAAO;oBACtB,QAAQ,EAAE,MAAM;oBAChB,IAAI,EAAE,SAAS;iBAChB,CAAC;YACJ,KAAK,GAAG;gBACN,IAAI,CAAC,SAAS,EAAE,CAAC;gBACjB,OAAO;oBACL,IAAI,EAAE,SAAS;oBACf,UAAU,EAAE,KAAK,CAAC,OAAO;oBACzB,OAAO,EAAE,KAAK,CAAC,OAAO;oBACtB,QAAQ,EAAE,KAAK,CAAC,QAAQ;oBACxB,IAAI,EAAE,QAAQ;iBACf,CAAC;YACJ,KAAK,GAAG,CAAC;YACT,KAAK,GAAG,CAAC;YACT,KAAK,GAAG,CAAC;YACT,KAAK,GAAG,CAAC;YACT,KAAK,GAAG,CAAC;YACT,KAAK,GAAG,CAAC;YACT,KAAK,GAAG,CAAC;YACT,KAAK,GAAG,CAAC;YACT,KAAK,GAAG,CAAC;YACT,KAAK,GAAG,CAAC;YACT,KAAK,GAAG;gBACN,IAAI,CAAC,SAAS,EAAE,CAAC;gBACjB,OAAO;oBACL,IAAI,EAAE,SAAS;oBACf,UAAU,EAAE,KAAK,CAAC,OAAO;oBACzB,OAAO,EAAE,KAAK,CAAC,OAAO;oBACtB,QAAQ,EAAE,KAAK,CAAC,QAAQ;oBACxB,IAAI,EAAE,QAAQ;iBACf,CAAC;QACN,CAAC;QAED,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC;YACf,IAAI,EAAE,OAAO;YACb,OAAO,EAAE,iBAAiB;YAC1B,OAAO,EAAE,IAAI,CAAC,SAAS,EAAE,CAAC,OAAO;SAClC,CAAC,CAAC;QACH,IAAI,CAAC,IAAI,EAAE,CAAC;QACZ,OAAO,SAAS,CAAC;IACnB,CAAC;IAEO,UAAU;QAChB,MAAM,WAAW,GAAG,IAAI,CAAC,SAAS,EAAE,CAAC;QACrC,MAAM,MAAM,GAAgB,EAAE,CAAC;QAC/B,OAAO,IAAI,EAAE,CAAC;YACZ,IAAI,IAAI,CAAC,SAAS,EAAE,CAAC,QAAQ,KAAK,GAAG,EAAE,CAAC;gBACtC,MAAM,YAAY,GAAG,IAAI,CAAC,SAAS,EAAE,CAAC;gBACtC,OAAO;oBACL,IAAI,EAAE,OAAO;oBACb,UAAU,EAAE,WAAW,CAAC,OAAO;oBAC/B,OAAO,EAAE;wBACP,KAAK,EAAE,WAAW,CAAC,OAAO,CAAC,KAAK;wBAChC,GAAG,EAAE,YAAY,CAAC,OAAO,CAAC,GAAG;qBAC9B;oBACD,MAAM;iBACP,CAAC;YACJ,CAAC;YACD,IAAI,IAAI,CAAC,SAAS,EAAE,CAAC,QAAQ,KAAK,GAAG,EAAE,CAAC;gBACtC,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC;oBACf,IAAI,EAAE,OAAO;oBACb,OAAO,EAAE,eAAe;oBACxB,OAAO,EAAE,IAAI,CAAC,SAAS,EAAE,CAAC,OAAO;iBAClC,CAAC,CAAC;gBACH,MAAM,YAAY,GAAG,IAAI,CAAC,SAAS,EAAE,CAAC;gBACtC,OAAO;oBACL,IAAI,EAAE,OAAO;oBACb,UAAU,EAAE,WAAW,CAAC,OAAO;oBAC/B,OAAO,EAAE;wBACP,KAAK,EAAE,WAAW,CAAC,OAAO,CAAC,KAAK;wBAChC,GAAG,EAAE,YAAY,CAAC,OAAO,CAAC,GAAG;qBAC9B;oBACD,MAAM;iBACP,CAAC;YACJ,CAAC;YACD,IAAI,IAAI,CAAC,SAAS,EAAE,CAAC,QAAQ,KAAK,EAAE,EAAE,CAAC;gBACrC,cAAc;gBACd,IAAI,CAAC,kBAAkB,CAAC,GAAG,CAAC,CAAC;gBAC7B,OAAO;oBACL,IAAI,EAAE,OAAO;oBACb,UAAU,EAAE,WAAW,CAAC,OAAO;oBAC/B,OAAO,EAAE;wBACP,KAAK,EAAE,WAAW,CAAC,OAAO,CAAC,KAAK;wBAChC,GAAG,EAAE,IAAI,CAAC,SAAS,EAAE,CAAC,OAAO,CAAC,KAAK;qBACpC;oBACD,MAAM;iBACP,CAAC;YACJ,CAAC;YACD,MAAM,KAAK,GAAG,IAAI,CAAC,gBAAgB,EAAE,CAAC;YACtC,IAAI,KAAK,EAAE,CAAC;gBACV,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;YACrB,CAAC;YACD,IAAI,IAAI,CAAC,SAAS,EAAE,CAAC,QAAQ,KAAK,GAAG,EAAE,CAAC;gBACtC,MAAM,UAAU,GAAG,IAAI,CAAC,SAAS,EAAE,CAAC;gBACpC,oCAAoC;gBACpC,IAAI,IAAI,CAAC,SAAS,EAAE,CAAC,QAAQ,KAAK,GAAG,EAAE,CAAC;oBACtC,yCAAyC;oBACzC,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC;wBACd,OAAO,EAAE,UAAU,CAAC,OAAO;wBAC3B,WAAW,EAAE,EAAE;qBAChB,CAAC,CAAC;gBACL,CAAC;YACH,CAAC;QACH,CAAC;IACH,CAAC;IAEO,WAAW;QACjB,MAAM,WAAW,GAAG,IAAI,CAAC,SAAS,EAAE,CAAC;QACrC,MAAM,SAAS,GAAoC,EAAE,CAAC;QACtD,MAAM,OAAO,GAAc,EAAE,CAAC;QAC9B,OAAO,IAAI,EAAE,CAAC;YACZ,IAAI,IAAI,CAAC,SAAS,EAAE,CAAC,QAAQ,KAAK,GAAG,EAAE,CAAC;gBACtC,MAAM,YAAY,GAAG,IAAI,CAAC,SAAS,EAAE,CAAC;gBACtC,OAAO;oBACL,IAAI,EAAE,QAAQ;oBACd,UAAU,EAAE,WAAW,CAAC,OAAO;oBAC/B,OAAO,EAAE;wBACP,KAAK,EAAE,WAAW,CAAC,OAAO,CAAC,KAAK;wBAChC,GAAG,EAAE,YAAY,CAAC,OAAO,CAAC,GAAG;qBAC9B;oBACD,SAAS;oBACT,OAAO;iBACR,CAAC;YACJ,CAAC;YACD,IAAI,IAAI,CAAC,SAAS,EAAE,CAAC,QAAQ,KAAK,GAAG,EAAE,CAAC;gBACtC,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC;oBACf,IAAI,EAAE,OAAO;oBACb,OAAO,EAAE,eAAe;oBACxB,OAAO,EAAE,IAAI,CAAC,SAAS,EAAE,CAAC,OAAO;iBAClC,CAAC,CAAC;gBACH,MAAM,YAAY,GAAG,IAAI,CAAC,SAAS,EAAE,CAAC;gBACtC,OAAO;oBACL,IAAI,EAAE,QAAQ;oBACd,UAAU,EAAE,WAAW,CAAC,OAAO;oBAC/B,OAAO,EAAE;wBACP,KAAK,EAAE,WAAW,CAAC,OAAO,CAAC,KAAK;wBAChC,GAAG,EAAE,YAAY,CAAC,OAAO,CAAC,GAAG;qBAC9B;oBACD,SAAS;oBACT,OAAO;iBACR,CAAC;YACJ,CAAC;YACD,IAAI,IAAI,CAAC,SAAS,EAAE,CAAC,QAAQ,KAAK,EAAE,EAAE,CAAC;gBACrC,cAAc;gBACd,IAAI,CAAC,kBAAkB,CAAC,GAAG,CAAC,CAAC;gBAC7B,OAAO;oBACL,IAAI,EAAE,QAAQ;oBACd,UAAU,EAAE,WAAW,CAAC,OAAO;oBAC/B,OAAO,EAAE;wBACP,KAAK,EAAE,WAAW,CAAC,OAAO,CAAC,KAAK;wBAChC,GAAG,EAAE,IAAI,CAAC,SAAS,EAAE,CAAC,OAAO,CAAC,KAAK;qBACpC;oBACD,SAAS;oBACT,OAAO;iBACR,CAAC;YACJ,CAAC;YACD,MAAM,QAAQ,GAAG,IAAI,CAAC,SAAS,EAAE,CAAC;YAClC,IAAI,CAAC,QAAQ,CAAC,QAAQ,CAAC,UAAU,CAAC,GAAG,CAAC,EAAE,CAAC;gBACvC,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC;oBACf,IAAI,EAAE,OAAO;oBACb,OAAO,EAAE,kBAAkB;oBAC3B,OAAO,EAAE,QAAQ,CAAC,OAAO;iBAC1B,CAAC,CAAC;gBACH,IAAI,CAAC,IAAI,EAAE,CAAC;gBACZ,6DAA6D;gBAC7D,IAAI,IAAI,CAAC,SAAS,EAAE,CAAC,QAAQ,KAAK,GAAG,EAAE,CAAC;oBACtC,IAAI,CAAC,SAAS,EAAE,CAAC;gBACnB,CAAC;gBACD,SAAS;YACX,CAAC;YACD,MAAM,GAAG,GAAG,IAAI,CAAC,KAAK,CAAC,QAAQ,CAAC,QAAQ,CAAW,CAAC;YACpD,OAAO,CAAC,IAAI,CAAC;gBACX,GAAG,EAAE,GAAG;gBACR,UAAU,EAAE,QAAQ,CAAC,OAAO;aAC7B,CAAC,CAAC;YACH,IAAI,CAAC,SAAS,EAAE,CAAC;YACjB,IAAI,CAAC,IAAI,CAAC,kBAAkB,CAAC,GAAG,CAAC,EAAE,CAAC;gBAClC,SAAS;YACX,CAAC;YACD,IAAI,SAAS,CAAC,GAAG,CAAC,EAAE,CAAC;gBACnB,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC;oBACf,IAAI,EAAE,OAAO;oBACb,OAAO,EAAE,eAAe;oBACxB,OAAO,EAAE,QAAQ,CAAC,OAAO;iBAC1B,CAAC,CAAC;YACL,CAAC;YACD,MAAM,KAAK,GAAG,IAAI,CAAC,gBAAgB,EAAE,CAAC;YACtC,IAAI,KAAK,EAAE,CAAC;gBACV,SAAS,CAAC,GAAG,CAAC,GAAG;oBACf,UAAU,EAAE,QAAQ,CAAC,OAAO;oBAC5B,GAAG,EAAE,GAAG;oBACR,KAAK,EAAE,KAAK;iBACb,CAAC;YACJ,CAAC;YACD,IAAI,IAAI,CAAC,SAAS,EAAE,CAAC,QAAQ,KAAK,GAAG,EAAE,CAAC;gBACtC,MAAM,UAAU,GAAG,IAAI,CAAC,SAAS,EAAE,CAAC;gBACpC,oCAAoC;gBACpC,IAAI,IAAI,CAAC,SAAS,EAAE,CAAC,QAAQ,KAAK,GAAG,EAAE,CAAC;oBACtC,yCAAyC;oBACzC,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC;wBACd,OAAO,EAAE,UAAU,CAAC,OAAO;wBAC3B,WAAW,EAAE,EAAE;qBAChB,CAAC,CAAC;gBACL,CAAC;YACH,CAAC;QACH,CAAC;IACH,CAAC;IAED,SAAS;QACP,MAAM,KAAK,GAAG,IAAI,CAAC,SAAS,EAAE,CAAC;QAC/B,IAAI,KAAK,CAAC,QAAQ,EAAE,CAAC;YACnB,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC;gBACf,IAAI,EAAE,OAAO;gBACb,OAAO,EAAE,eAAe;gBACxB,OAAO,EAAE,IAAI,CAAC,SAAS,EAAE,CAAC,OAAO;aAClC,CAAC,CAAC;QACL,CAAC;IACH,CAAC;IAEO,SAAS;QACf,MAAM,MAAM,GAAG,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC;QAE5C,2DAA2D;QAC3D,CAAC;YACC,MAAM,QAAQ,GACZ,IAAI,CAAC,UAAU,IAAI,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,UAAU,GAAG,CAAC,CAAC,CAAC;YACtE,MAAM,gBAAgB,GAAY;gBAChC,KAAK,EAAE,QAAQ,CAAC,CAAC,CAAC,QAAQ,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC;gBAC1C,GAAG,EAAE,MAAM,CAAC,OAAO,CAAC,KAAK;aAC1B,CAAC;YACF,MAAM,eAAe,GAAG,IAAI,CAAC,KAAK,CAAC,SAAS,CAC1C,gBAAgB,CAAC,KAAK,EACtB,gBAAgB,CAAC,GAAG,CACrB,CAAC;YACF,MAAM,iBAAiB,GAAG,IAAI,CAAC,wBAAwB,CACrD,QAAQ,EAAE,QAAQ,IAAI,EAAE,EACxB,MAAM,CAAC,QAAQ,CAChB,CAAC;YAEF,IAAI,eAAe,KAAK,iBAAiB,CAAC,IAAI,EAAE,CAAC;gBAC/C,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC;oBACd,OAAO,EAAE,gBAAgB;oBACzB,WAAW,EAAE,iBAAiB,CAAC,IAAI;iBACpC,CAAC,CAAC;YACL,CAAC;YACD,IAAI,CAAC,MAAM,GAAG,iBAAiB,CAAC,SAAS,IAAI,IAAI,CAAC,MAAM,CAAC;QAC3D,CAAC;QAED,EAAE,IAAI,CAAC,UAAU,CAAC;QAClB,OAAO,MAAM,CAAC;IAChB,CAAC;IAEO,wBAAwB,CAAC,CAAS,EAAE,CAAS;QACnD,MAAM,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC;QACxB,IAAI,CAAC,KAAK,GAAG,EAAE,CAAC;YACd,OAAO;gBACL,IAAI,EAAE,GAAG;aACV,CAAC;QACJ,CAAC;aAAM,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC,KAAK,GAAG,EAAE,CAAC;YAC/C,OAAO;gBACL,IAAI,EAAE,KAAK,MAAM,EAAE;aACpB,CAAC;QACJ,CAAC;aAAM,IAAI,cAAc,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,eAAe,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC;YAC7D,kEAAkE;YAClE,OAAO;gBACL,IAAI,EAAE,MAAM,MAAM,EAAE;aACrB,CAAC;QACJ,CAAC;aAAM,IAAI,CAAC,CAAC,KAAK,GAAG,IAAI,CAAC,KAAK,GAAG,CAAC,IAAI,CAAC,CAAC,KAAK,GAAG,IAAI,CAAC,KAAK,GAAG,CAAC,EAAE,CAAC;YAChE,MAAM,SAAS,GAAG,MAAM,GAAG,WAAW,CAAC;YACvC,OAAO;gBACL,IAAI,EAAE,KAAK,SAAS,EAAE;gBACtB,SAAS,EAAE,SAAS;aACrB,CAAC;QACJ,CAAC;aAAM,IAAI,CAAC,CAAC,KAAK,GAAG,IAAI,CAAC,KAAK,GAAG,CAAC,IAAI,CAAC,CAAC,KAAK,GAAG,IAAI,CAAC,KAAK,GAAG,CAAC,EAAE,CAAC;YAChE,MAAM,SAAS,GAAG,MAAM,CAAC,OAAO,CAAC,WAAW,EAAE,EAAE,CAAC,CAAC;YAClD,OAAO;gBACL,IAAI,EAAE,KAAK,SAAS,EAAE;gBACtB,SAAS,EAAE,SAAS;aACrB,CAAC;QACJ,CAAC;aAAM,CAAC;YACN,OAAO;gBACL,IAAI,EAAE,EAAE;aACT,CAAC;QACJ,CAAC;IACH,CAAC;IAEO,SAAS;QACf,OAAO,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC;IACtC,CAAC;IAEO,kBAAkB,CAAC,MAAc;QACvC,IAAI,IAAI,CAAC,SAAS,EAAE,CAAC,QAAQ,KAAK,MAAM,EAAE,CAAC;YACzC,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC;gBACf,IAAI,EAAE,OAAO;gBACb,OAAO,EAAE,cAAc,MAAM,GAAG;gBAChC,OAAO,EAAE,IAAI,CAAC,SAAS,EAAE,CAAC,OAAO;aAClC,CAAC,CAAC;YACH,IAAI,CAAC,IAAI,EAAE,CAAC;YACZ,OAAO,KAAK,CAAC;QACf,CAAC;QACD,IAAI,CAAC,SAAS,EAAE,CAAC;QACjB,OAAO,IAAI,CAAC;IACd,CAAC;IAEO,IAAI;QACV,OAAO,IAAI,EAAE,CAAC;YACZ,MAAM,SAAS,GAAG,IAAI,CAAC,SAAS,EAAE,CAAC,QAAQ,CAAC;YAC5C,IACE,SAAS,KAAK,EAAE;gBAChB,SAAS,KAAK,GAAG;gBACjB,SAAS,KAAK,GAAG;gBACjB,SAAS,KAAK,GAAG;gBACjB,SAAS,CAAC,UAAU,CAAC,GAAG,CAAC,EACzB,CAAC;gBACD,OAAO;YACT,CAAC;iBAAM,IAAI,SAAS,KAAK,GAAG,EAAE,CAAC;gBAC7B,IAAI,CAAC,UAAU,EAAE,CAAC;YACpB,CAAC;iBAAM,IAAI,SAAS,KAAK,GAAG,EAAE,CAAC;gBAC7B,IAAI,CAAC,WAAW,EAAE,CAAC;YACrB,CAAC;iBAAM,CAAC;gBACN,IAAI,CAAC,SAAS,EAAE,CAAC;YACnB,CAAC;QACH,CAAC;IACH,CAAC;CACF;AASD,MAAM,WAAW,GAAG,IAAI,CAAC","sourcesContent":["import type {\n JsonArray,\n JsonEdit,\n JsonError,\n JsonKey,\n JsonKeyValue,\n JsonObject,\n JsonParseResult,\n JsonValue,\n Segment,\n} from \"./types\";\n\nexport function parseJsonValue(input: string): JsonParseResult {\n const tokens = tokenize(input);\n if (tokens.kind === \"error\") {\n return {\n value: undefined,\n errors: [tokens],\n edits: [],\n };\n }\n const parser = new JsonParser(tokens.tokens, input);\n const parseResult = parser.parseValueOrSkip();\n parser.expectEnd();\n\n return {\n value: parseResult,\n errors: parser.errors,\n edits: parser.edits,\n };\n}\n\ninterface JsonToken {\n segment: Segment;\n jsonCode: string;\n}\n\ninterface JsonTokens {\n kind: \"tokens\";\n tokens: JsonToken[];\n}\n\nfunction tokenize(input: string): JsonTokens | JsonError {\n const tokens: JsonToken[] = [];\n let pos = 0;\n\n const whitespaceRegex = /[ \\t\\r\\n]*/y;\n const tokenRegex =\n /([[\\]{}:,]|(-?(?:0|[1-9]\\d*)(?:\\.\\d+)?(?:[eE][+-]?\\d+)?)|false|true|null|(\"(((?=\\\\)\\\\([\"\\\\/ bfnrt]|u[0-9a-fA-F]{4}))|[^\"\\\\\\0-\\x1F\\x7F]+)*\")|$)/y;\n\n while (true) {\n whitespaceRegex.lastIndex = pos;\n whitespaceRegex.exec(input);\n pos = whitespaceRegex.lastIndex;\n\n tokenRegex.lastIndex = pos;\n const tokenMatch = tokenRegex.exec(input);\n if (tokenMatch) {\n const tokenText = tokenMatch[0];\n const segment: Segment = {\n start: pos,\n end: pos + tokenText.length,\n };\n const token: JsonToken = { segment, jsonCode: tokenText };\n pos = tokenRegex.lastIndex;\n tokens.push(token);\n if (tokenText === \"\") {\n return {\n kind: \"tokens\",\n tokens: tokens,\n };\n }\n } else {\n // Find the next word boundary using unicode support\n const wordBoundaryRegex = /\\w*/uy;\n wordBoundaryRegex.lastIndex = pos + 1;\n wordBoundaryRegex.exec(input);\n const end = wordBoundaryRegex.lastIndex || pos + 1;\n return {\n kind: \"error\",\n message: \"not a token\",\n segment: { start: pos, end: end },\n };\n }\n }\n}\n\nclass JsonParser {\n constructor(private tokens: JsonToken[], private readonly input: string) {}\n private tokenIndex = 0;\n errors: JsonError[] = [];\n edits: JsonEdit[] = [];\n private indent = \"\";\n\n parseValueOrSkip(): JsonValue | undefined {\n const token = this.peekToken();\n const firstChar = token.jsonCode ? token.jsonCode[0] : \"\";\n\n switch (firstChar) {\n case \"[\":\n return this.parseArray();\n case \"{\":\n return this.parseObject();\n case \"n\":\n this.nextToken();\n return {\n kind: \"literal\",\n firstToken: token.segment,\n segment: token.segment,\n jsonCode: \"null\",\n type: \"null\",\n };\n case \"f\":\n this.nextToken();\n return {\n kind: \"literal\",\n firstToken: token.segment,\n segment: token.segment,\n jsonCode: \"false\",\n type: \"boolean\",\n };\n case \"t\":\n this.nextToken();\n return {\n kind: \"literal\",\n firstToken: token.segment,\n segment: token.segment,\n jsonCode: \"true\",\n type: \"boolean\",\n };\n case '\"':\n this.nextToken();\n return {\n kind: \"literal\",\n firstToken: token.segment,\n segment: token.segment,\n jsonCode: token.jsonCode,\n type: \"string\",\n };\n case \"0\":\n case \"1\":\n case \"2\":\n case \"3\":\n case \"4\":\n case \"5\":\n case \"6\":\n case \"7\":\n case \"8\":\n case \"9\":\n case \"-\":\n this.nextToken();\n return {\n kind: \"literal\",\n firstToken: token.segment,\n segment: token.segment,\n jsonCode: token.jsonCode,\n type: \"number\",\n };\n }\n\n this.errors.push({\n kind: \"error\",\n message: \"expected: value\",\n segment: this.peekToken().segment,\n });\n this.skip();\n return undefined;\n }\n\n private parseArray(): JsonArray {\n const leftBracket = this.nextToken();\n const values: JsonValue[] = [];\n while (true) {\n if (this.peekToken().jsonCode === \"]\") {\n const rightBracket = this.nextToken();\n return {\n kind: \"array\",\n firstToken: leftBracket.segment,\n segment: {\n start: leftBracket.segment.start,\n end: rightBracket.segment.end,\n },\n values,\n };\n }\n if (this.peekToken().jsonCode === \"}\") {\n this.errors.push({\n kind: \"error\",\n message: \"expected: ']'\",\n segment: this.peekToken().segment,\n });\n const wrongBracket = this.nextToken();\n return {\n kind: \"array\",\n firstToken: leftBracket.segment,\n segment: {\n start: leftBracket.segment.start,\n end: wrongBracket.segment.end,\n },\n values,\n };\n }\n if (this.peekToken().jsonCode === \"\") {\n // End of file\n this.expectSymbolOrSkip(\"]\");\n return {\n kind: \"array\",\n firstToken: leftBracket.segment,\n segment: {\n start: leftBracket.segment.start,\n end: this.peekToken().segment.start,\n },\n values,\n };\n }\n const value = this.parseValueOrSkip();\n if (value) {\n values.push(value);\n }\n if (this.peekToken().jsonCode === \",\") {\n const commaToken = this.nextToken();\n // Check if this is a trailing comma\n if (this.peekToken().jsonCode === \"]\") {\n // Trailing comma - add edit to remove it\n this.edits.push({\n segment: commaToken.segment,\n replacement: \"\",\n });\n }\n }\n }\n }\n\n private parseObject(): JsonObject {\n const leftBracket = this.nextToken();\n const keyValues: { [key: string]: JsonKeyValue } = {};\n const allKeys: JsonKey[] = [];\n while (true) {\n if (this.peekToken().jsonCode === \"}\") {\n const rightBracket = this.nextToken();\n return {\n kind: \"object\",\n firstToken: leftBracket.segment,\n segment: {\n start: leftBracket.segment.start,\n end: rightBracket.segment.end,\n },\n keyValues,\n allKeys,\n };\n }\n if (this.peekToken().jsonCode === \"]\") {\n this.errors.push({\n kind: \"error\",\n message: \"expected: ']'\",\n segment: this.peekToken().segment,\n });\n const wrongBracket = this.nextToken();\n return {\n kind: \"object\",\n firstToken: leftBracket.segment,\n segment: {\n start: leftBracket.segment.start,\n end: wrongBracket.segment.end,\n },\n keyValues,\n allKeys,\n };\n }\n if (this.peekToken().jsonCode === \"\") {\n // End of file\n this.expectSymbolOrSkip(\"}\");\n return {\n kind: \"object\",\n firstToken: leftBracket.segment,\n segment: {\n start: leftBracket.segment.start,\n end: this.peekToken().segment.start,\n },\n keyValues,\n allKeys,\n };\n }\n const keyToken = this.peekToken();\n if (!keyToken.jsonCode.startsWith('\"')) {\n this.errors.push({\n kind: \"error\",\n message: \"expected: string\",\n segment: keyToken.segment,\n });\n this.skip();\n // Consume comma if we're stuck at one to avoid infinite loop\n if (this.peekToken().jsonCode === \",\") {\n this.nextToken();\n }\n continue;\n }\n const key = JSON.parse(keyToken.jsonCode) as string;\n allKeys.push({\n key: key,\n keySegment: keyToken.segment,\n });\n this.nextToken();\n if (!this.expectSymbolOrSkip(\":\")) {\n continue;\n }\n if (keyValues[key]) {\n this.errors.push({\n kind: \"error\",\n message: \"duplicate key\",\n segment: keyToken.segment,\n });\n }\n const value = this.parseValueOrSkip();\n if (value) {\n keyValues[key] = {\n keySegment: keyToken.segment,\n key: key,\n value: value,\n };\n }\n if (this.peekToken().jsonCode === \",\") {\n const commaToken = this.nextToken();\n // Check if this is a trailing comma\n if (this.peekToken().jsonCode === \"}\") {\n // Trailing comma - add edit to remove it\n this.edits.push({\n segment: commaToken.segment,\n replacement: \"\",\n });\n }\n }\n }\n }\n\n expectEnd(): void {\n const token = this.nextToken();\n if (token.jsonCode) {\n this.errors.push({\n kind: \"error\",\n message: \"expected: end\",\n segment: this.peekToken().segment,\n });\n }\n }\n\n private nextToken(): JsonToken {\n const result = this.tokens[this.tokenIndex];\n\n // Check the whitespace separator before the current token.\n {\n const previous =\n this.tokenIndex <= 0 ? undefined : this.tokens[this.tokenIndex - 1];\n const separatorSegment: Segment = {\n start: previous ? previous.segment.end : 0,\n end: result.segment.start,\n };\n const actualSeparator = this.input.substring(\n separatorSegment.start,\n separatorSegment.end,\n );\n const expectedSeparator = this.inferWhitespaceSeparator(\n previous?.jsonCode ?? \"\",\n result.jsonCode,\n );\n\n if (actualSeparator !== expectedSeparator.text) {\n this.edits.push({\n segment: separatorSegment,\n replacement: expectedSeparator.text,\n });\n }\n this.indent = expectedSeparator.newIndent ?? this.indent;\n }\n\n ++this.tokenIndex;\n return result;\n }\n\n private inferWhitespaceSeparator(a: string, b: string): WhitespaceSeparator {\n const { indent } = this;\n if (a === \":\") {\n return {\n text: \" \",\n };\n } else if (a === \",\" && b !== \"]\" && b !== \"}\") {\n return {\n text: `\\n${indent}`,\n };\n } else if (/[0-9\"}\\]el]$/.test(a) && /^[0-9\"{[tfn-]/.test(b)) {\n // a is the end of a JSON value and B is the start of a JSON value\n return {\n text: `,\\n${indent}`,\n };\n } else if ((a === \"[\" && b !== \"]\") || (a === \"{\" && b !== \"}\")) {\n const newIndent = indent + INDENT_UNIT;\n return {\n text: `\\n${newIndent}`,\n newIndent: newIndent,\n };\n } else if ((a !== \"[\" && b === \"]\") || (a !== \"{\" && b === \"}\")) {\n const newIndent = indent.replace(INDENT_UNIT, \"\");\n return {\n text: `\\n${newIndent}`,\n newIndent: newIndent,\n };\n } else {\n return {\n text: \"\",\n };\n }\n }\n\n private peekToken(): JsonToken {\n return this.tokens[this.tokenIndex];\n }\n\n private expectSymbolOrSkip(symbol: string): boolean {\n if (this.peekToken().jsonCode !== symbol) {\n this.errors.push({\n kind: \"error\",\n message: `expected: '${symbol}'`,\n segment: this.peekToken().segment,\n });\n this.skip();\n return false;\n }\n this.nextToken();\n return true;\n }\n\n private skip(): void {\n while (true) {\n const tokenJson = this.peekToken().jsonCode;\n if (\n tokenJson === \"\" ||\n tokenJson === \",\" ||\n tokenJson === \"]\" ||\n tokenJson === \"}\" ||\n tokenJson.startsWith('\"')\n ) {\n return;\n } else if (tokenJson === \"[\") {\n this.parseArray();\n } else if (tokenJson === \"{\") {\n this.parseObject();\n } else {\n this.nextToken();\n }\n }\n }\n}\n\n/// Text to insert between two consecutive tokens.\ninterface WhitespaceSeparator {\n /// Matches /(,?)(\\n?)( )*/\n text: string;\n newIndent?: string;\n}\n\nconst INDENT_UNIT = \" \";\n"]}
1
+ {"version":3,"file":"json_parser.js","sourceRoot":"","sources":["../../src/json/json_parser.ts"],"names":[],"mappings":"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","sourcesContent":["import type {\n JsonArray,\n JsonEdit,\n JsonError,\n JsonKey,\n JsonKeyValue,\n JsonObject,\n JsonParseResult,\n JsonValue,\n Segment,\n} from \"./types\";\n\nexport function parseJsonValue(input: string): JsonParseResult {\n const tokens = tokenize(input);\n if (tokens.kind === \"error\") {\n return {\n value: undefined,\n errors: [tokens],\n edits: [],\n };\n }\n const parser = new JsonParser(tokens.tokens, input);\n const parseResult = parser.parseValueOrSkip();\n parser.expectEnd();\n\n return {\n value: parseResult,\n errors: parser.errors,\n edits: parser.edits,\n };\n}\n\ninterface JsonToken {\n segment: Segment;\n jsonCode: string;\n indent: number;\n}\n\ninterface JsonTokens {\n kind: \"tokens\";\n tokens: JsonToken[];\n}\n\nfunction tokenize(input: string): JsonTokens | JsonError {\n const tokens: JsonToken[] = [];\n let pos = 0;\n let lineIndent = 0;\n let lineHasContent = false;\n\n const whitespaceRegex = /[ \\t\\r\\n]*/y;\n const tokenRegex =\n /([[\\]{}:,]|(-?(?:0|[1-9]\\d*)(?:\\.\\d+)?(?:[eE][+-]?\\d+)?)|false|true|null|(\"(((?=\\\\)\\\\([\"\\\\/ bfnrt]|u[0-9a-fA-F]{4}))|[^\"\\\\\\0-\\x1F\\x7F]+)*\")|$)/y;\n\n while (true) {\n const beforeWhitespacePos = pos;\n whitespaceRegex.lastIndex = pos;\n whitespaceRegex.exec(input);\n pos = whitespaceRegex.lastIndex;\n\n for (let i = beforeWhitespacePos; i < pos; ++i) {\n const ch = input[i];\n if (ch === \"\\n\") {\n lineIndent = 0;\n lineHasContent = false;\n } else if (!lineHasContent && (ch === \" \" || ch === \"\\t\")) {\n lineIndent++;\n }\n }\n\n tokenRegex.lastIndex = pos;\n const tokenMatch = tokenRegex.exec(input);\n if (tokenMatch) {\n const tokenText = tokenMatch[0];\n const segment: Segment = {\n start: pos,\n end: pos + tokenText.length,\n };\n const token: JsonToken = {\n segment,\n jsonCode: tokenText,\n indent: lineIndent,\n };\n pos = tokenRegex.lastIndex;\n tokens.push(token);\n if (tokenText !== \"\") {\n lineHasContent = true;\n }\n if (tokenText === \"\") {\n return {\n kind: \"tokens\",\n tokens: tokens,\n };\n }\n } else {\n // Find the next word boundary using unicode support\n const wordBoundaryRegex = /\\w*/uy;\n wordBoundaryRegex.lastIndex = pos + 1;\n wordBoundaryRegex.exec(input);\n const end = wordBoundaryRegex.lastIndex || pos + 1;\n return {\n kind: \"error\",\n message: \"not a token\",\n segment: { start: pos, end: end },\n };\n }\n }\n}\n\nclass JsonParser {\n constructor(private tokens: JsonToken[], private readonly input: string) {}\n private tokenIndex = 0;\n errors: JsonError[] = [];\n edits: JsonEdit[] = [];\n private indent = \"\";\n\n parseValueOrSkip(): JsonValue | undefined {\n const token = this.peekToken();\n const firstChar = token.jsonCode ? token.jsonCode[0] : \"\";\n\n const { indent } = token;\n\n switch (firstChar) {\n case \"[\":\n return this.parseArray();\n case \"{\":\n return this.parseObject();\n case \"n\":\n this.nextToken();\n return {\n kind: \"literal\",\n firstToken: token.segment,\n segment: token.segment,\n jsonCode: \"null\",\n type: \"null\",\n indent,\n };\n case \"f\":\n this.nextToken();\n return {\n kind: \"literal\",\n firstToken: token.segment,\n segment: token.segment,\n jsonCode: \"false\",\n type: \"boolean\",\n indent,\n };\n case \"t\":\n this.nextToken();\n return {\n kind: \"literal\",\n firstToken: token.segment,\n segment: token.segment,\n jsonCode: \"true\",\n type: \"boolean\",\n indent,\n };\n case '\"':\n this.nextToken();\n return {\n kind: \"literal\",\n firstToken: token.segment,\n segment: token.segment,\n jsonCode: token.jsonCode,\n type: \"string\",\n indent,\n };\n case \"0\":\n case \"1\":\n case \"2\":\n case \"3\":\n case \"4\":\n case \"5\":\n case \"6\":\n case \"7\":\n case \"8\":\n case \"9\":\n case \"-\":\n this.nextToken();\n return {\n kind: \"literal\",\n firstToken: token.segment,\n segment: token.segment,\n jsonCode: token.jsonCode,\n type: \"number\",\n indent,\n };\n }\n\n this.errors.push({\n kind: \"error\",\n message: \"expected: value\",\n segment: this.peekToken().segment,\n });\n this.skip();\n return undefined;\n }\n\n private parseArray(): JsonArray {\n const leftBracket = this.nextToken();\n const { indent } = leftBracket;\n const values: JsonValue[] = [];\n while (true) {\n if (this.peekToken().jsonCode === \"]\") {\n const rightBracket = this.nextToken();\n return {\n kind: \"array\",\n firstToken: leftBracket.segment,\n segment: {\n start: leftBracket.segment.start,\n end: rightBracket.segment.end,\n },\n values,\n indent,\n };\n }\n if (this.peekToken().jsonCode === \"}\") {\n this.errors.push({\n kind: \"error\",\n message: \"expected: ']'\",\n segment: this.peekToken().segment,\n });\n const wrongBracket = this.nextToken();\n return {\n kind: \"array\",\n firstToken: leftBracket.segment,\n segment: {\n start: leftBracket.segment.start,\n end: wrongBracket.segment.end,\n },\n values,\n indent,\n };\n }\n if (this.peekToken().jsonCode === \"\") {\n // End of file\n this.expectSymbolOrSkip(\"]\");\n return {\n kind: \"array\",\n firstToken: leftBracket.segment,\n segment: {\n start: leftBracket.segment.start,\n end: this.peekToken().segment.start,\n },\n values,\n indent,\n };\n }\n const value = this.parseValueOrSkip();\n if (value) {\n values.push(value);\n }\n if (this.peekToken().jsonCode === \",\") {\n const commaToken = this.nextToken();\n // Check if this is a trailing comma\n if (this.peekToken().jsonCode === \"]\") {\n // Trailing comma - add edit to remove it\n this.edits.push({\n segment: commaToken.segment,\n replacement: \"\",\n });\n }\n }\n }\n }\n\n private parseObject(): JsonObject {\n const leftBracket = this.nextToken();\n const { indent } = leftBracket;\n const keyValues: { [key: string]: JsonKeyValue } = {};\n const allKeys: JsonKey[] = [];\n while (true) {\n if (this.peekToken().jsonCode === \"}\") {\n const rightBracket = this.nextToken();\n return {\n kind: \"object\",\n firstToken: leftBracket.segment,\n segment: {\n start: leftBracket.segment.start,\n end: rightBracket.segment.end,\n },\n keyValues,\n allKeys,\n indent,\n };\n }\n if (this.peekToken().jsonCode === \"]\") {\n this.errors.push({\n kind: \"error\",\n message: \"expected: ']'\",\n segment: this.peekToken().segment,\n });\n const wrongBracket = this.nextToken();\n return {\n kind: \"object\",\n firstToken: leftBracket.segment,\n segment: {\n start: leftBracket.segment.start,\n end: wrongBracket.segment.end,\n },\n keyValues,\n allKeys,\n indent,\n };\n }\n if (this.peekToken().jsonCode === \"\") {\n // End of file\n this.expectSymbolOrSkip(\"}\");\n return {\n kind: \"object\",\n firstToken: leftBracket.segment,\n segment: {\n start: leftBracket.segment.start,\n end: this.peekToken().segment.start,\n },\n keyValues,\n allKeys,\n indent,\n };\n }\n const keyToken = this.peekToken();\n if (!keyToken.jsonCode.startsWith('\"')) {\n this.errors.push({\n kind: \"error\",\n message: \"expected: string\",\n segment: keyToken.segment,\n });\n this.skip();\n // Consume comma if we're stuck at one to avoid infinite loop\n if (this.peekToken().jsonCode === \",\") {\n this.nextToken();\n }\n continue;\n }\n const key = JSON.parse(keyToken.jsonCode) as string;\n allKeys.push({\n key: key,\n keySegment: keyToken.segment,\n });\n this.nextToken();\n if (!this.expectSymbolOrSkip(\":\")) {\n continue;\n }\n if (keyValues[key]) {\n this.errors.push({\n kind: \"error\",\n message: \"duplicate key\",\n segment: keyToken.segment,\n });\n }\n const value = this.parseValueOrSkip();\n if (value) {\n keyValues[key] = {\n keySegment: keyToken.segment,\n key: key,\n value: value,\n };\n }\n if (this.peekToken().jsonCode === \",\") {\n const commaToken = this.nextToken();\n // Check if this is a trailing comma\n if (this.peekToken().jsonCode === \"}\") {\n // Trailing comma - add edit to remove it\n this.edits.push({\n segment: commaToken.segment,\n replacement: \"\",\n });\n }\n }\n }\n }\n\n expectEnd(): void {\n const token = this.nextToken();\n if (token.jsonCode) {\n this.errors.push({\n kind: \"error\",\n message: \"expected: end\",\n segment: this.peekToken().segment,\n });\n }\n }\n\n private nextToken(): JsonToken {\n const result = this.tokens[this.tokenIndex];\n\n // Check the whitespace separator before the current token.\n {\n const previous =\n this.tokenIndex <= 0 ? undefined : this.tokens[this.tokenIndex - 1];\n const separatorSegment: Segment = {\n start: previous ? previous.segment.end : 0,\n end: result.segment.start,\n };\n const actualSeparator = this.input.substring(\n separatorSegment.start,\n separatorSegment.end,\n );\n const expectedSeparator = this.inferWhitespaceSeparator(\n previous?.jsonCode ?? \"\",\n result.jsonCode,\n );\n\n if (actualSeparator !== expectedSeparator.text) {\n this.edits.push({\n segment: separatorSegment,\n replacement: expectedSeparator.text,\n });\n }\n this.indent = expectedSeparator.newIndent ?? this.indent;\n }\n\n ++this.tokenIndex;\n return result;\n }\n\n private inferWhitespaceSeparator(a: string, b: string): WhitespaceSeparator {\n const { indent } = this;\n if (a === \":\") {\n return {\n text: \" \",\n };\n } else if (a === \",\" && b !== \"]\" && b !== \"}\") {\n return {\n text: `\\n${indent}`,\n };\n } else if (/[0-9\"}\\]el]$/.test(a) && /^[0-9\"{[tfn-]/.test(b)) {\n // a is the end of a JSON value and B is the start of a JSON value\n return {\n text: `,\\n${indent}`,\n };\n } else if ((a === \"[\" && b !== \"]\") || (a === \"{\" && b !== \"}\")) {\n const newIndent = indent + INDENT_UNIT;\n return {\n text: `\\n${newIndent}`,\n newIndent: newIndent,\n };\n } else if ((a !== \"[\" && b === \"]\") || (a !== \"{\" && b === \"}\")) {\n const newIndent = indent.replace(INDENT_UNIT, \"\");\n return {\n text: `\\n${newIndent}`,\n newIndent: newIndent,\n };\n } else {\n return {\n text: \"\",\n };\n }\n }\n\n private peekToken(): JsonToken {\n return this.tokens[this.tokenIndex];\n }\n\n private expectSymbolOrSkip(symbol: string): boolean {\n if (this.peekToken().jsonCode !== symbol) {\n this.errors.push({\n kind: \"error\",\n message: `expected: '${symbol}'`,\n segment: this.peekToken().segment,\n });\n this.skip();\n return false;\n }\n this.nextToken();\n return true;\n }\n\n private skip(): void {\n while (true) {\n const tokenJson = this.peekToken().jsonCode;\n if (\n tokenJson === \"\" ||\n tokenJson === \",\" ||\n tokenJson === \"]\" ||\n tokenJson === \"}\" ||\n tokenJson.startsWith('\"')\n ) {\n return;\n } else if (tokenJson === \"[\") {\n this.parseArray();\n } else if (tokenJson === \"{\") {\n this.parseObject();\n } else {\n this.nextToken();\n }\n }\n }\n}\n\n/// Text to insert between two consecutive tokens.\ninterface WhitespaceSeparator {\n /// Matches /(,?)(\\n?)( )*/\n text: string;\n newIndent?: string;\n}\n\nconst INDENT_UNIT = \" \";\n"]}
@@ -57,6 +57,17 @@ describe("json_parser", () => {
57
57
  edits: [],
58
58
  });
59
59
  });
60
+ it("tracks indent for top-level literal", () => {
61
+ expect(parseJsonValue(" true")).toMatch({
62
+ value: {
63
+ kind: "literal",
64
+ jsonCode: "true",
65
+ type: "boolean",
66
+ indent: 3,
67
+ },
68
+ errors: [],
69
+ });
70
+ });
60
71
  it("parses empty array", () => {
61
72
  expect(parseJsonValue("[]")).toMatch({
62
73
  value: { kind: "array", values: [] },
@@ -109,6 +120,43 @@ describe("json_parser", () => {
109
120
  ],
110
121
  });
111
122
  });
123
+ it("tracks indent from line leading spaces for field values", () => {
124
+ const result = parseJsonValue(`{
125
+ "a": 1,
126
+ "b": [
127
+ 2
128
+ ]
129
+ }`);
130
+ expect(result).toMatch({
131
+ value: {
132
+ kind: "object",
133
+ indent: 0,
134
+ keyValues: {
135
+ a: {
136
+ value: {
137
+ kind: "literal",
138
+ jsonCode: "1",
139
+ indent: 2,
140
+ },
141
+ },
142
+ b: {
143
+ value: {
144
+ kind: "array",
145
+ indent: 2,
146
+ values: [
147
+ {
148
+ kind: "literal",
149
+ jsonCode: "2",
150
+ indent: 4,
151
+ },
152
+ ],
153
+ },
154
+ },
155
+ },
156
+ },
157
+ errors: [],
158
+ });
159
+ });
112
160
  it("parses arrays with whitespace", () => {
113
161
  expect(parseJsonValue(" [ 1 ] ")).toMatch({
114
162
  value: {