Skip to content

Fix jsonc parser issue with quotes in strings #15

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Apr 13, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 4 additions & 4 deletions src/objdictgen/jsonod.py
Original file line number Diff line number Diff line change
Expand Up @@ -167,10 +167,10 @@ class ValidationError(Exception):

# Remove jsonc annotations
# Copied from https://github.com/NickolaiBeloguzov/jsonc-parser/blob/master/jsonc_parser/parser.py#L11-L39
RE_JSONC = re.compile(r"(\".*?\"|\'.*?\')|(/\*.*?\*/|//[^\r\n]*$)", re.MULTILINE | re.DOTALL)
RE_JSONC = re.compile(r"(\".*?(?<!\\)\"|\'.*?\')|(\s*/\*.*?\*/\s*|\s*//[^\r\n]*$)", re.MULTILINE | re.DOTALL)


def remove_jasonc(text: str) -> str:
def remove_jsonc(text: str) -> str:
""" Remove jsonc annotations """
def _re_sub(match: re.Match[str]) -> str:
if match.group(2) is not None:
Expand Down Expand Up @@ -406,7 +406,7 @@ def generate_node(contents: str|TODJson) -> "Node":
if isinstance(contents, str):

# Remove jsonc annotations
jsontext = remove_jasonc(contents)
jsontext = remove_jsonc(contents)

# Load the json
jd: TODJson = json.loads(jsontext)
Expand All @@ -426,7 +426,7 @@ def generate_node(contents: str|TODJson) -> "Node":
global SCHEMA # pylint: disable=global-statement
if not SCHEMA:
with open(objdictgen.JSON_SCHEMA, 'r', encoding="utf-8") as f:
SCHEMA = json.loads(remove_jasonc(f.read()))
SCHEMA = json.loads(remove_jsonc(f.read()))

if SCHEMA and jd.get('$version') == JSON_VERSION:
jsonschema.validate(jd, schema=SCHEMA)
Expand Down
44 changes: 43 additions & 1 deletion tests/test_jsonod.py
Original file line number Diff line number Diff line change
@@ -1,9 +1,51 @@
import pytest
from pprint import pprint
from objdictgen import Node
from objdictgen.jsonod import generate_jsonc, generate_node
from objdictgen.jsonod import generate_jsonc, generate_node, remove_jsonc
from .test_odcompare import shave_equal


def test_jsonod_remove_jsonc():
""" Test that the remove_jsonc function works as expected. """

out = remove_jsonc("""{
"a": "abc", // remove
"b": 42
}""")
assert out == """{
"a": "abc",
"b": 42
}"""

# This was a bug where there quoted string made jsonc parsing fail
out = remove_jsonc("""{
"a": "a\\"bc", // remove
"b": 42
}""")
assert out == """{
"a": "a\\"bc",
"b": 42
}"""

out = remove_jsonc("""{
"a": "a\\"bc", /* remove it */ "c": 42,
"b": 42
}""")
assert out == """{
"a": "a\\"bc","c": 42,
"b": 42
}"""

out = remove_jsonc("""{
"a": "a'bc", // remove
"b": 42
}""")
assert out == """{
"a": "a'bc",
"b": 42
}"""


def test_jsonod_roundtrip(odjsoneds):
""" Test that the file can be exported to json and that the loaded file
is equal to the first.
Expand Down