Skip to content

Commit 172bd8a

Browse files
authored
Merge pull request #11 from Artifizer/main
fix: fix recently broken codebase and revert the changes back
2 parents 98c4510 + fd5206b commit 172bd8a

8 files changed

Lines changed: 168 additions & 133 deletions

File tree

gts/src/gts/entities.py

Lines changed: 11 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,14 @@
11
from __future__ import annotations
22

33
from dataclasses import dataclass, field
4-
from typing import Any, Dict, List, Optional, Set, Tuple
4+
from typing import TYPE_CHECKING, Any, Dict, List, Optional, Set, Tuple
55

66
from .gts import GtsID
7-
from .path_resolver import GtsPathResolver
87
from .schema_cast import GtsEntityCastResult, SchemaCastError
98

9+
if TYPE_CHECKING:
10+
from .path_resolver import GtsPathResolver
11+
1012

1113
@dataclass
1214
class ValidationError:
@@ -166,16 +168,18 @@ def _is_json_schema_entity(self) -> bool:
166168
return True
167169
return False
168170

169-
def resolve_path(self, path: str) -> JsonPathResolver:
170-
resolver = JsonPathResolver(self.gts_id.id if self.gts_id else "", self.content)
171+
def resolve_path(self, path: str) -> "GtsPathResolver":
172+
from .path_resolver import GtsPathResolver
173+
174+
resolver = GtsPathResolver(self.gts_id.id if self.gts_id else "", self.content)
171175
return resolver.resolve(path)
172176

173177
def cast(
174178
self,
175-
to_schema: JsonEntity,
176-
from_schema: JsonEntity,
179+
to_schema: "GtsEntity",
180+
from_schema: "GtsEntity",
177181
resolver: Optional[Any] = None,
178-
) -> JsonEntityCastResult:
182+
) -> GtsEntityCastResult:
179183
if self.is_schema:
180184
# When casting a schema, from_schema might be a standard JSON Schema (no gts_id)
181185
# In that case, skip the sanity check

gts/src/gts/files_reader.py

Lines changed: 5 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,7 @@ def __init__(self, path: str | List[str], cfg: Optional[GtsConfig] = None) -> No
4141

4242
def _collect_files(self) -> None:
4343
"""Collect all JSON and YAML files from the specified paths, following symlinks."""
44-
valid_extensions = {'.json', '.jsonc', '.gts', '.yaml', '.yml'}
44+
valid_extensions = {".json", ".jsonc", ".gts", ".yaml", ".yml"}
4545
seen: set[str] = set()
4646
collected: List[Path] = []
4747

@@ -77,7 +77,7 @@ def _collect_files(self) -> None:
7777
def _load_file(self, file_path: Path) -> Any:
7878
"""Load content from JSON or YAML file."""
7979
with file_path.open("r", encoding="utf-8") as f:
80-
if file_path.suffix.lower() in {'.yaml', '.yml'}:
80+
if file_path.suffix.lower() in {".yaml", ".yml"}:
8181
return yaml.safe_load(f)
8282
else:
8383
return json.load(f)
@@ -89,29 +89,21 @@ def _process_file(self, file_path: Path) -> List[GtsEntity]:
8989
try:
9090
content = self._load_file(file_path)
9191
json_file = GtsFile(
92-
path=str(file_path),
93-
name=file_path.name,
94-
content=content
92+
path=str(file_path), name=file_path.name, content=content
9593
)
9694

9795
# Handle both single objects and arrays
9896
if isinstance(content, list):
9997
for idx, item in enumerate(content):
10098
entity = GtsEntity(
101-
file=json_file,
102-
list_sequence=idx,
103-
content=item,
104-
cfg=self.cfg
99+
file=json_file, list_sequence=idx, content=item, cfg=self.cfg
105100
)
106101
if entity.gts_id:
107102
logging.debug(f"- discovered entity: {entity.gts_id.id}")
108103
entities.append(entity)
109104
else:
110105
entity = GtsEntity(
111-
file=json_file,
112-
list_sequence=None,
113-
content=content,
114-
cfg=self.cfg
106+
file=json_file, list_sequence=None, content=content, cfg=self.cfg
115107
)
116108
if entity.gts_id:
117109
logging.debug(f"- discovered entity: {entity.gts_id.id}")

gts/src/gts/ops.py

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -314,7 +314,7 @@ def reload_from_path(self, path: str | List[str]) -> None:
314314
def add_entity(
315315
self, content: Dict[str, Any], validate: bool = False
316316
) -> GtsAddEntityResult:
317-
entity = JsonEntity(content=content, cfg=self.cfg)
317+
entity = GtsEntity(content=content, cfg=self.cfg)
318318
if not entity.gts_id:
319319
return GtsAddEntityResult(
320320
ok=False, error="Unable to detect GTS ID in entity"
@@ -433,33 +433,33 @@ def schema_graph(self, gts_id: str) -> GtsSchemaGraphResult:
433433

434434
def compatibility(
435435
self, old_schema_id: str, new_schema_id: str
436-
) -> JsonEntityCastResult:
436+
) -> GtsEntityCastResult:
437437
return self.store.is_minor_compatible(old_schema_id, new_schema_id)
438438

439-
def cast(self, from_id: str, to_schema_id: str) -> JsonEntityCastResult:
439+
def cast(self, from_id: str, to_schema_id: str) -> GtsEntityCastResult:
440440
try:
441441
return self.store.cast(from_id, to_schema_id)
442442
except Exception as e:
443-
return JsonEntityCastResult(error=str(e))
443+
return GtsEntityCastResult(error=str(e))
444444

445445
def query(self, expr: str, limit: int = 100) -> GtsStoreQueryResult:
446446
return self.store.query(expr, limit)
447447

448-
def attr(self, gts_with_path: str) -> JsonPathResolver:
448+
def attr(self, gts_with_path: str) -> GtsPathResolver:
449449
gts, path = GtsID.split_at_path(gts_with_path)
450450
if path is None:
451-
return JsonPathResolver(gts_id=gts, content=None).failure(
451+
return GtsPathResolver(gts_id=gts, content=None).failure(
452452
"", "Attribute selector requires '@path' in the identifier"
453453
)
454454
entity = self.store.get(gts)
455455
if not entity:
456-
return JsonPathResolver(gts_id=gts, content=None).failure(
456+
return GtsPathResolver(gts_id=gts, content=None).failure(
457457
path, f"Entity not found: {gts}"
458458
)
459459
return entity.resolve_path(path)
460460

461461
def extract_id(self, content: Dict[str, Any]) -> GtsExtractIdResult:
462-
entity = JsonEntity(content=content, cfg=self.cfg)
462+
entity = GtsEntity(content=content, cfg=self.cfg)
463463
return GtsExtractIdResult(
464464
id=entity.gts_id.id if entity.gts_id else "",
465465
schema_id=entity.schemaId,

gts/src/gts/schema_cast.py

Lines changed: 56 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -295,25 +295,41 @@ def _cast_instance_to_schema(
295295
p_type = p_schema.get("type")
296296
if p_type == "object" and isinstance(val, dict):
297297
nested_schema = GtsEntityCastResult._effective_object_schema(p_schema)
298-
new_obj, add_sub, rem_sub, new_incompatibility_reasons = GtsEntityCastResult._cast_instance_to_schema(
299-
val, nested_schema, base_path=(f"{base_path}.{prop}" if base_path else prop), incompatibility_reasons=incompatibility_reasons
298+
new_obj, add_sub, rem_sub, new_incompatibility_reasons = (
299+
GtsEntityCastResult._cast_instance_to_schema(
300+
val,
301+
nested_schema,
302+
base_path=(f"{base_path}.{prop}" if base_path else prop),
303+
incompatibility_reasons=incompatibility_reasons,
304+
)
300305
)
301306
result[prop] = new_obj
302307
added.extend(add_sub)
303308
removed.extend(rem_sub)
304309
incompatibility_reasons.extend(new_incompatibility_reasons)
305310
elif p_type == "array" and isinstance(val, list):
306311
items_schema = p_schema.get("items")
307-
if isinstance(items_schema, dict) and items_schema.get("type") == "object":
308-
nested_schema = GtsEntityCastResult._effective_object_schema(items_schema)
312+
if (
313+
isinstance(items_schema, dict)
314+
and items_schema.get("type") == "object"
315+
):
316+
nested_schema = GtsEntityCastResult._effective_object_schema(
317+
items_schema
318+
)
309319
new_list: List[Any] = []
310320
for idx, item in enumerate(val):
311321
if isinstance(item, dict):
312-
new_item, add_sub, rem_sub, new_incompatibility_reasons = GtsEntityCastResult._cast_instance_to_schema(
313-
item,
314-
nested_schema,
315-
base_path=(f"{base_path}.{prop}[{idx}]" if base_path else f"{prop}[{idx}]"),
316-
incompatibility_reasons=incompatibility_reasons,
322+
new_item, add_sub, rem_sub, new_incompatibility_reasons = (
323+
GtsEntityCastResult._cast_instance_to_schema(
324+
item,
325+
nested_schema,
326+
base_path=(
327+
f"{base_path}.{prop}[{idx}]"
328+
if base_path
329+
else f"{prop}[{idx}]"
330+
),
331+
incompatibility_reasons=incompatibility_reasons,
332+
)
317333
)
318334
new_list.append(new_item)
319335
added.extend(add_sub)
@@ -481,23 +497,38 @@ def _check_constraint_compatibility(
481497
if prop_type in ("number", "integer"):
482498
errors.extend(
483499
GtsEntityCastResult._check_min_max_constraint(
484-
prop, old_prop_schema, new_prop_schema, "minimum", "maximum", check_tightening
500+
prop,
501+
old_prop_schema,
502+
new_prop_schema,
503+
"minimum",
504+
"maximum",
505+
check_tightening,
485506
)
486507
)
487508

488509
# String constraints
489510
if prop_type == "string":
490511
errors.extend(
491512
GtsEntityCastResult._check_min_max_constraint(
492-
prop, old_prop_schema, new_prop_schema, "minLength", "maxLength", check_tightening
513+
prop,
514+
old_prop_schema,
515+
new_prop_schema,
516+
"minLength",
517+
"maxLength",
518+
check_tightening,
493519
)
494520
)
495521

496522
# Array constraints
497523
if prop_type == "array":
498524
errors.extend(
499525
GtsEntityCastResult._check_min_max_constraint(
500-
prop, old_prop_schema, new_prop_schema, "minItems", "maxItems", check_tightening
526+
prop,
527+
old_prop_schema,
528+
new_prop_schema,
529+
"minItems",
530+
"maxItems",
531+
check_tightening,
501532
)
502533
)
503534

@@ -588,8 +619,10 @@ def _check_schema_compatibility(
588619

589620
# Recursively check nested object properties
590621
if old_type == "object" and new_type == "object":
591-
nested_compat, nested_errors = GtsEntityCastResult._check_schema_compatibility(
592-
old_prop_schema, new_prop_schema, check_backward
622+
nested_compat, nested_errors = (
623+
GtsEntityCastResult._check_schema_compatibility(
624+
old_prop_schema, new_prop_schema, check_backward
625+
)
593626
)
594627
if not nested_compat:
595628
for err in nested_errors:
@@ -615,7 +648,9 @@ def _check_backward_compatibility(
615648
- Cannot add enum values
616649
- Cannot tighten constraints (decrease max, increase min, etc.)
617650
"""
618-
return GtsEntityCastResult._check_schema_compatibility(old_schema, new_schema, check_backward=True)
651+
return GtsEntityCastResult._check_schema_compatibility(
652+
old_schema, new_schema, check_backward=True
653+
)
619654

620655
@staticmethod
621656
def _check_forward_compatibility(
@@ -634,7 +669,9 @@ def _check_forward_compatibility(
634669
- Cannot remove enum values
635670
- Cannot relax constraints (increase max, decrease min, etc.)
636671
"""
637-
return GtsEntityCastResult._check_schema_compatibility(old_schema, new_schema, check_backward=False)
672+
return GtsEntityCastResult._check_schema_compatibility(
673+
old_schema, new_schema, check_backward=False
674+
)
638675

639676
@staticmethod
640677
def _diff_objects(
@@ -697,7 +734,9 @@ def _only_optional_add_remove(
697734
) -> bool:
698735
if not isinstance(a, dict) or not isinstance(b, dict):
699736
if a != b:
700-
reasons.append(f"{GtsEntityCastResult._path_label(path)}: value changed")
737+
reasons.append(
738+
f"{GtsEntityCastResult._path_label(path)}: value changed"
739+
)
701740
return False
702741
return True
703742

gts/src/gts/store.py

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -115,7 +115,7 @@ def __init__(self, reader: GtsReader) -> None:
115115
Args:
116116
reader: GtsReader instance to populate entities from
117117
"""
118-
self._by_id: Dict[str, JsonEntity] = {}
118+
self._by_id: Dict[str, GtsEntity] = {}
119119
self._reader = reader
120120

121121
# Populate entities from reader if provided
@@ -148,7 +148,7 @@ def register_schema(self, type_id: str, schema: Dict[str, Any]) -> None:
148148
raise ValueError("Schema type_id must end with '~'")
149149
# parse sanity
150150
gts_id = GtsID(type_id)
151-
entity = JsonEntity(content=schema, gts_id=gts_id, is_schema=True)
151+
entity = GtsEntity(content=schema, gts_id=gts_id, is_schema=True)
152152
self._by_id[type_id] = entity
153153

154154
def get(self, entity_id: str) -> Optional[GtsEntity]:
@@ -369,7 +369,7 @@ def is_minor_compatible(
369369
new_entity = self.get(new_schema_id)
370370

371371
if not old_entity or not new_entity:
372-
return JsonEntityCastResult(
372+
return GtsEntityCastResult(
373373
from_id=old_schema_id,
374374
to_id=new_schema_id,
375375
direction="unknown",
@@ -390,16 +390,16 @@ def is_minor_compatible(
390390

391391
# Use the cast method's compatibility checking logic
392392
is_backward, backward_errors = (
393-
JsonEntityCastResult._check_backward_compatibility(old_schema, new_schema)
393+
GtsEntityCastResult._check_backward_compatibility(old_schema, new_schema)
394394
)
395-
is_forward, forward_errors = JsonEntityCastResult._check_forward_compatibility(
395+
is_forward, forward_errors = GtsEntityCastResult._check_forward_compatibility(
396396
old_schema, new_schema
397397
)
398398

399399
# Determine direction
400-
direction = JsonEntityCastResult._infer_direction(old_schema_id, new_schema_id)
400+
direction = GtsEntityCastResult._infer_direction(old_schema_id, new_schema_id)
401401

402-
return JsonEntityCastResult(
402+
return GtsEntityCastResult(
403403
from_id=old_schema_id,
404404
to_id=new_schema_id,
405405
direction=direction,

0 commit comments

Comments
 (0)