Skip to content

Commit 7afabfd

Browse files
committed
Schema: implementation for Examples()
1 parent 1b114ef commit 7afabfd

File tree

3 files changed

+62
-4
lines changed

3 files changed

+62
-4
lines changed

schema.go

Lines changed: 21 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -14,9 +14,10 @@ var (
1414
)
1515

1616
var (
17-
pathSchDef = cue.MakePath(cue.Hid("_#schema", "github.com/grafana/thema"))
18-
pathSch = cue.MakePath(cue.Str("schema"))
19-
pathJoin = cue.MakePath(cue.Hid("_join", "github.com/grafana/thema"))
17+
pathSchDef = cue.MakePath(cue.Hid("_#schema", "github.com/grafana/thema"))
18+
pathExamples = cue.MakePath(cue.Str("examples"))
19+
pathSch = cue.MakePath(cue.Str("schema"))
20+
pathJoin = cue.MakePath(cue.Hid("_join", "github.com/grafana/thema"))
2021
)
2122

2223
// schemaDef represents a single #SchemaDef, with a backlink to its containing
@@ -37,7 +38,23 @@ type schemaDef struct {
3738
// Examples returns the set of examples of this schema defined in the original
3839
// lineage. The string key is the name given to the example.
3940
func (sch *schemaDef) Examples() map[string]*Instance {
40-
panic("TODO")
41+
examplesNode := sch.Underlying().LookupPath(pathExamples)
42+
it, err := examplesNode.Fields()
43+
if err != nil {
44+
panic(err)
45+
}
46+
47+
examples := make(map[string]*Instance)
48+
for it.Next() {
49+
label := it.Label()
50+
examples[label] = &Instance{
51+
raw: it.Value(),
52+
name: label,
53+
sch: sch,
54+
}
55+
}
56+
57+
return examples
4158
}
4259

4360
func (sch *schemaDef) rt() *Runtime {

schema_test.go

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,9 @@ import (
77

88
"cuelang.org/go/cue/cuecontext"
99
"cuelang.org/go/cue/errors"
10+
11+
"github.com/stretchr/testify/assert"
12+
"github.com/stretchr/testify/require"
1013
)
1114

1215
var linstr = `name: "single"
@@ -17,6 +20,13 @@ schemas: [{
1720
anint: int64 | *42
1821
abool: bool
1922
}
23+
examples: {
24+
simple: {
25+
astring: "some string"
26+
anint: 42
27+
abool: true
28+
}
29+
}
2030
}]
2131
`
2232

@@ -76,6 +86,33 @@ func TestBindType(t *testing.T) {
7686
}
7787
}
7888

89+
func TestSchema_Examples(t *testing.T) {
90+
lin := testLin()
91+
92+
sch := lin.First()
93+
examples := sch.Examples()
94+
require.NotNil(t, examples)
95+
96+
// There must be a "simple" example based on
97+
// the definition above (beginning of file).
98+
require.NotEmpty(t, examples)
99+
require.NotNil(t, examples["simple"])
100+
101+
tt := &TestType{}
102+
ts, err := BindType[*TestType](sch, tt)
103+
require.NoError(t, err)
104+
105+
tinst, err := ts.ValidateTyped(examples["simple"].Underlying())
106+
require.NoError(t, err)
107+
108+
val, err := tinst.Value()
109+
require.NoError(t, err)
110+
111+
assert.Equal(t, "some string", *val.Astring)
112+
assert.Equal(t, int64(42), val.Anint)
113+
assert.Equal(t, true, val.Abool)
114+
}
115+
79116
// scratch test, preserved only as a simpler sandbox for future playing with pointers, generics, reflect
80117
func testPointerNewVar(t *testing.T) {
81118
type Foo struct {

surface.go

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -215,6 +215,10 @@ type Schema interface {
215215
// Lineage returns the lineage that contains this schema.
216216
Lineage() Lineage
217217

218+
// Examples returns the set of examples of this schema defined in the original
219+
// lineage. The string key is the name given to the example.
220+
Examples() map[string]*Instance
221+
218222
// Schema must be a private interface in order to ensure all instances fully
219223
// conform to Thema invariants.
220224
_schema()

0 commit comments

Comments
 (0)