From bd21f5151e14547b001a2db93afb3d8eb0bbe37c Mon Sep 17 00:00:00 2001 From: Santhosh Kumar Tekuri Date: Mon, 22 Apr 2024 12:32:43 +0530 Subject: [PATCH] roots: extract getMeta --- root.go | 7 +++ roots.go | 86 ++++++++++++++++++----------------- testdata/invalid_schemas.json | 2 +- 3 files changed, 52 insertions(+), 43 deletions(-) diff --git a/root.go b/root.go index 46050e6..405d89a 100644 --- a/root.go +++ b/root.go @@ -178,6 +178,13 @@ func newResource(ptr jsonPointer, id url) *resource { return &resource{ptr: ptr, id: id, anchors: make(map[anchor]jsonPointer)} } +//-- + +type meta struct { + draft *Draft + vocabs []string +} + // -- type UnsupportedVocabularyError struct { diff --git a/roots.go b/roots.go index 6c8f87a..49bfbd9 100644 --- a/roots.go +++ b/roots.go @@ -55,61 +55,63 @@ func (rr *roots) orLoad(u url) (*root, error) { return rr.addRoot(u, doc, make(map[url]struct{})) } -func (rr *roots) addRoot(u url, doc any, cycle map[url]struct{}) (*root, error) { - draft, vocabs, err := func() (*Draft, []string, error) { - obj, ok := doc.(map[string]any) - if !ok { - return rr.defaultDraft, nil, nil - } - sch, ok := strVal(obj, "$schema") - if !ok { - return rr.defaultDraft, nil, nil - } - if draft := draftFromURL(sch); draft != nil { - return draft, nil, nil - } - sch, _ = split(sch) - if _, err := gourl.Parse(sch); err != nil { - return nil, nil, &InvalidMetaSchemaURLError{u.String(), err} - } - schUrl := url(sch) - if r, ok := rr.roots[schUrl]; ok { - vocabs, err := r.getReqdVocabs() - return r.draft, vocabs, err - } - if schUrl == u { - return nil, nil, &UnsupportedDraftError{schUrl.String()} - } - if _, ok := cycle[schUrl]; ok { - return nil, nil, &MetaSchemaCycleError{u.String()} - } - cycle[schUrl] = struct{}{} - doc, err := rr.loadURL(schUrl) - if err != nil { - return nil, nil, err - } - r, err := rr.addRoot(schUrl, doc, cycle) - if err != nil { - return nil, nil, err - } +func (rr *roots) getMeta(up urlPtr, doc any, cycle map[url]struct{}) (meta, error) { + obj, ok := doc.(map[string]any) + if !ok { + return meta{rr.defaultDraft, nil}, nil + } + sch, ok := strVal(obj, "$schema") + if !ok { + return meta{rr.defaultDraft, nil}, nil + } + if draft := draftFromURL(sch); draft != nil { + return meta{draft, nil}, nil + } + sch, _ = split(sch) + if _, err := gourl.Parse(sch); err != nil { + return meta{}, &InvalidMetaSchemaURLError{up.String(), err} + } + schUrl := url(sch) + if r, ok := rr.roots[schUrl]; ok { vocabs, err := r.getReqdVocabs() - return r.draft, vocabs, err - }() + return meta{r.draft, vocabs}, err + } + if schUrl == up.url { + return meta{}, &UnsupportedDraftError{schUrl.String()} + } + if _, ok := cycle[schUrl]; ok { + return meta{}, &MetaSchemaCycleError{schUrl.String()} + } + cycle[schUrl] = struct{}{} + doc, err := rr.loadURL(schUrl) + if err != nil { + return meta{}, err + } + r, err := rr.addRoot(schUrl, doc, cycle) + if err != nil { + return meta{}, err + } + vocabs, err := r.getReqdVocabs() + return meta{r.draft, vocabs}, err +} + +func (rr *roots) addRoot(u url, doc any, cycle map[url]struct{}) (*root, error) { + meta, err := rr.getMeta(urlPtr{u, ""}, doc, cycle) if err != nil { return nil, err } resources := map[jsonPointer]*resource{} - if err := draft.collectResources(doc, u, "", u, resources); err != nil { + if err := meta.draft.collectResources(doc, u, "", u, resources); err != nil { return nil, err } r := &root{ url: u, doc: doc, - draft: draft, + draft: meta.draft, resources: resources, - metaVocabs: vocabs, + metaVocabs: meta.vocabs, } if !strings.HasPrefix(u.String(), "http://json-schema.org/") && !strings.HasPrefix(u.String(), "https://json-schema.org/") { diff --git a/testdata/invalid_schemas.json b/testdata/invalid_schemas.json index bf29046..1cd7410 100644 --- a/testdata/invalid_schemas.json +++ b/testdata/invalid_schemas.json @@ -186,7 +186,7 @@ "$schema": "http://remotes/a.json" }, "errors": [ - "MetaSchemaCycleError{URL:\"http://remotes/b.json\"}" + "MetaSchemaCycleError{URL:\"http://remotes/a.json\"}" ] }, {