Skip to content

Commit 116d9e4

Browse files
author
Peter Amstutz
committed
Merge branch 'resolve_all_refactor'
Conflicts: schema_salad/ref_resolver.py
2 parents ad8a111 + 33ef215 commit 116d9e4

File tree

1 file changed

+80
-59
lines changed

1 file changed

+80
-59
lines changed

schema_salad/ref_resolver.py

Lines changed: 80 additions & 59 deletions
Original file line numberDiff line numberDiff line change
@@ -322,6 +322,81 @@ def resolve_ref(self, ref, base_url=None, checklinks=True):
322322
except TypeError:
323323
return obj, metadata
324324

325+
326+
def _resolve_idmap(self, document, loader):
327+
# Convert fields with mapSubject into lists
328+
# use mapPredicate if the mapped value isn't a dict.
329+
for idmapField in loader.idmap:
330+
if (idmapField in document and isinstance(document[idmapField], dict) and
331+
"$import" not in document[idmapField] and
332+
"$include" not in document[idmapField]):
333+
ls = []
334+
for k in sorted(document[idmapField].keys()):
335+
v = document[idmapField][k]
336+
if not isinstance(v, dict):
337+
if idmapField in loader.mapPredicate:
338+
v = {loader.mapPredicate[idmapField]: v}
339+
else:
340+
raise validate.ValidationException(
341+
"mapSubject '%s' value '%s' is not a dict and does not have a mapPredicate", k, v)
342+
v[loader.idmap[idmapField]] = k
343+
ls.append(v)
344+
document[idmapField] = ls
345+
346+
def _resolve_identifier(self, document, loader, base_url):
347+
# Expand identifier field (usually 'id') to resolve scope
348+
for identifer in loader.identifiers:
349+
if identifer in document:
350+
if isinstance(document[identifer], basestring):
351+
document[identifer] = loader.expand_url(
352+
document[identifer], base_url, scoped=True)
353+
if document[identifer] not in loader.idx or isinstance(loader.idx[document[identifer]], basestring):
354+
loader.idx[document[identifer]] = document
355+
base_url = document[identifer]
356+
else:
357+
raise validate.ValidationException(
358+
"identifier field '%s' must be a string" % (document[identifer]))
359+
return base_url
360+
361+
def _resolve_identity(self, document, loader, base_url):
362+
# Resolve scope for identity fields (fields where the value is the
363+
# identity of a standalone node, such as enum symbols)
364+
for identifer in loader.identity_links:
365+
if identifer in document and isinstance(document[identifer], list):
366+
for n, v in enumerate(document[identifer]):
367+
if isinstance(document[identifer][n], basestring):
368+
document[identifer][n] = loader.expand_url(
369+
document[identifer][n], base_url, scoped=True)
370+
if document[identifer][n] not in loader.idx:
371+
loader.idx[document[identifer][
372+
n]] = document[identifer][n]
373+
374+
def _normalize_fields(self, document, loader):
375+
# Normalize fields which are prefixed or full URIn to vocabulary terms
376+
for d in document:
377+
d2 = loader.expand_url(d, "", scoped=False, vocab_term=True)
378+
if d != d2:
379+
document[d2] = document[d]
380+
del document[d]
381+
382+
def _resolve_uris(self, document, loader, base_url):
383+
# Resolve remaining URLs based on document base
384+
for d in loader.url_fields:
385+
if d in self.scoped_ref_fields:
386+
continue
387+
if d in document:
388+
if isinstance(document[d], basestring):
389+
document[d] = loader.expand_url(
390+
document[d], base_url, scoped=False, vocab_term=(d in loader.vocab_fields))
391+
elif isinstance(document[d], list):
392+
document[d] = [
393+
loader.expand_url(
394+
url, base_url, scoped=False,
395+
vocab_term=(d in loader.vocab_fields))
396+
if isinstance(url, (str, unicode))
397+
else url for url in document[d]]
398+
399+
325400
def resolve_all(self, document, base_url, file_base=None, checklinks=True):
326401
# type: (Any, Union[str, unicode], Union[str, unicode], bool) -> Tuple[Any, Dict[str, Any]]
327402
loader = self
@@ -371,65 +446,11 @@ def resolve_all(self, document, base_url, file_base=None, checklinks=True):
371446
metadata, _ = loader.resolve_all(metadata, base_url, file_base=file_base, checklinks=False)
372447

373448
if isinstance(document, dict):
374-
for idmapField in loader.idmap:
375-
if (idmapField in document and isinstance(document[idmapField], dict) and
376-
"$import" not in document[idmapField] and
377-
"$include" not in document[idmapField]):
378-
ls = []
379-
for k in sorted(document[idmapField].keys()):
380-
v = document[idmapField][k]
381-
if not isinstance(v, dict):
382-
if idmapField in loader.mapPredicate:
383-
v = {loader.mapPredicate[idmapField]: v}
384-
else:
385-
raise validate.ValidationException(
386-
"mapSubject '%s' value '%s' is not a dict and does not have a mapPredicate" % (k, v))
387-
v[loader.idmap[idmapField]] = k
388-
ls.append(v)
389-
document[idmapField] = ls
390-
391-
for identifer in loader.identifiers:
392-
if identifer in document:
393-
if isinstance(document[identifer], basestring):
394-
document[identifer] = loader.expand_url(
395-
document[identifer], base_url, scoped=True)
396-
if document[identifer] not in loader.idx or isinstance(loader.idx[document[identifer]], basestring):
397-
loader.idx[document[identifer]] = document
398-
base_url = document[identifer]
399-
else:
400-
raise validate.ValidationException(
401-
"identifier field '%s' must be a string" % (document[identifer]))
402-
403-
for identifer in loader.identity_links:
404-
if identifer in document and isinstance(document[identifer], list):
405-
for n, v in enumerate(document[identifer]):
406-
if isinstance(document[identifer][n], basestring):
407-
document[identifer][n] = loader.expand_url(
408-
document[identifer][n], base_url, scoped=True)
409-
if document[identifer][n] not in loader.idx:
410-
loader.idx[document[identifer][
411-
n]] = document[identifer][n]
412-
413-
for d in document:
414-
d2 = loader.expand_url(d, "", scoped=False, vocab_term=True)
415-
if d != d2:
416-
document[d2] = document[d]
417-
del document[d]
418-
419-
for d in loader.url_fields:
420-
if d in self.scoped_ref_fields:
421-
continue
422-
if d in document:
423-
if isinstance(document[d], basestring):
424-
document[d] = loader.expand_url(
425-
document[d], base_url, scoped=False, vocab_term=(d in loader.vocab_fields))
426-
elif isinstance(document[d], list):
427-
document[d] = [
428-
loader.expand_url(
429-
url, base_url, scoped=False,
430-
vocab_term=(d in loader.vocab_fields))
431-
if isinstance(url, (str, unicode))
432-
else url for url in document[d]]
449+
self._resolve_idmap(document, loader)
450+
base_url = self._resolve_identifier(document, loader, base_url)
451+
self._resolve_identity(document, loader, base_url)
452+
self._normalize_fields(document, loader)
453+
self._resolve_uris(document, loader, base_url)
433454

434455
try:
435456
for key, val in document.items():

0 commit comments

Comments
 (0)