11import os .path
22from collections import defaultdict
33from hed .schema import from_string , load_schema , from_dataframes
4+ from hed .schema import hed_cache
45from hed .errors import get_printable_issue_string , HedFileError
56from hed .errors .error_types import ErrorSeverity
67from hed .schema .schema_comparer import SchemaComparer
78
89all_extensions = [".tsv" , ".mediawiki" , ".xml" , ".json" ]
910
1011
12+ def _is_prerelease_partner (base_schema ) -> bool :
13+ """Return True if base_schema's withStandard partner is only resolvable from the prerelease cache.
14+
15+ When a library schema serialised with ``save_merged=False`` is reloaded, the loader
16+ re-fetches the standard schema named in the ``withStandard`` header attribute. If
17+ that version lives only in the prerelease subdirectory of the cache, the reload will
18+ fail unless ``check_prerelease=True`` is forwarded. This helper detects that
19+ condition by asking the cache whether the version is found without the prerelease
20+ flag (not found → prerelease required).
21+
22+ Parameters:
23+ base_schema (HedSchema): The schema to inspect.
24+
25+ Returns:
26+ bool: True if ``withStandard`` is set and the version is absent from the
27+ regular (non-prerelease) cache directory.
28+ """
29+ with_standard = base_schema .with_standard
30+ if not with_standard :
31+ return False
32+ return hed_cache .get_hed_version_path (with_standard , check_prerelease = False ) is None
33+
34+
1135def validate_schema_object (base_schema , schema_name ):
1236 """Validate a schema object by checking compliance and roundtrip conversion.
1337
@@ -30,10 +54,16 @@ def validate_schema_object(base_schema, schema_name):
3054 validation_issues .append (error_message )
3155 return validation_issues
3256
57+ # If the withStandard partner only exists in the prerelease cache, all unmerged
58+ # reloads must pass check_prerelease=True or they will fail partner resolution.
59+ check_prerelease = _is_prerelease_partner (base_schema )
60+
3361 for save_merged in (True , False ):
3462 label = "merged" if save_merged else "unmerged"
3563 tagged_name = f"{ schema_name } ({ label } )"
36- validation_issues += _roundtrip_all_formats (base_schema , tagged_name , save_merged = save_merged )
64+ validation_issues += _roundtrip_all_formats (
65+ base_schema , tagged_name , save_merged = save_merged , check_prerelease = check_prerelease
66+ )
3767 except HedFileError as e :
3868 print (f"Saving/loading error: { schema_name } { e .message } " )
3969 error_text = e .message
@@ -291,7 +321,7 @@ def get_prerelease_path(repo_path, schema_name, schema_version):
291321 return os .path .join (base_path , "hedtsv" , schema_filename )
292322
293323
294- def _roundtrip_all_formats (base_schema , schema_name , save_merged = True ):
324+ def _roundtrip_all_formats (base_schema , schema_name , save_merged = True , check_prerelease = False ):
295325 """Roundtrip a schema through all four formats and compare to the original.
296326
297327 Serializes the schema to mediawiki, XML, JSON, and TSV, reloads each, and
@@ -302,26 +332,32 @@ def _roundtrip_all_formats(base_schema, schema_name, save_merged=True):
302332 schema_name (str): Label for error reporting (should include merge context).
303333 save_merged (bool): If True, save the merged (with-standard) form.
304334 If False, save only the library-specific content.
335+ check_prerelease (bool): If True, pass check_prerelease=True to all reload
336+ calls. Required when the schema's withStandard partner exists only in
337+ the prerelease cache directory; otherwise unmerged reloads will fail
338+ partner resolution. Has no effect when save_merged=True because the
339+ merged serialisation embeds the full standard content and no partner
340+ lookup is performed on reload.
305341
306342 Returns:
307343 list: A list of validation issue strings. Empty if no issues found.
308344 """
309345 issues = []
310346
311347 mediawiki_string = base_schema .get_as_mediawiki_string (save_merged = save_merged )
312- reloaded_schema = from_string (mediawiki_string , schema_format = ".mediawiki" )
348+ reloaded_schema = from_string (mediawiki_string , schema_format = ".mediawiki" , check_prerelease = check_prerelease )
313349 issues += _get_schema_comparison (base_schema , reloaded_schema , schema_name , "mediawiki" )
314350
315351 xml_string = base_schema .get_as_xml_string (save_merged = save_merged )
316- reloaded_schema = from_string (xml_string , schema_format = ".xml" )
352+ reloaded_schema = from_string (xml_string , schema_format = ".xml" , check_prerelease = check_prerelease )
317353 issues += _get_schema_comparison (base_schema , reloaded_schema , schema_name , "xml" )
318354
319355 json_string = base_schema .get_as_json_string (save_merged = save_merged )
320- reloaded_schema = from_string (json_string , schema_format = ".json" )
356+ reloaded_schema = from_string (json_string , schema_format = ".json" , check_prerelease = check_prerelease )
321357 issues += _get_schema_comparison (base_schema , reloaded_schema , schema_name , "json" )
322358
323359 tsv_dataframes = base_schema .get_as_dataframes (save_merged = save_merged )
324- reloaded_schema = from_dataframes (tsv_dataframes )
360+ reloaded_schema = from_dataframes (tsv_dataframes , check_prerelease = check_prerelease )
325361 issues += _get_schema_comparison (base_schema , reloaded_schema , schema_name , "tsv" )
326362
327363 return issues
0 commit comments