#name: optionals with label filters
#evalFull
# Tests that optional fields with label filters enforce their constraints:
# fields not matching the pattern or constraint fail with "field not allowed"
# or bound violations. jobs is the happy path; jobs1, jobs2, jobs3 are faulty.
-- in.cue --
#JobID: =~"^[a-zA-Z]*$"
#Job: {
	name: string
	cmd:  string
}
#Jobs: {
	{[#JobID]: #Job}

	{[=~"Test$"]: name: =~"^test"}// Must work without ...
}

jobs: foo: name: "allGood"
jobs: foo: name: "allGood"

jobs1:          #Jobs
jobs1: foo1: {} // faulty
@test(err, code=eval, at=jobs1.foo1, contains="field not allowed", pos=[-1:8])

jobs2: #Jobs
jobs2: fooTest: name: "badName" // faulty
@test(err, code=eval, at=jobs2.fooTest.name, contains="invalid value", pos=[-12:22, -18:8, -1:23])

jobs3: #Jobs
jobs3: [string]: #Job
jobs3: fooTest1: name: "badName" // faulty
@test(err, code=eval, at=jobs3.fooTest1, contains="field not allowed", pos=[-2:8, -1:8])

-- out/errors.txt --
[eval] jobs1.foo1: field not allowed:
    ./in.cue:16:8
[eval] jobs2.fooTest.name: invalid value "badName" (out of bound =~"^test"):
    ./in.cue:9:22
    ./in.cue:3:8
    ./in.cue:20:23
[eval] jobs3.fooTest1: field not allowed:
    ./in.cue:24:8
    ./in.cue:25:8
-- out/todo.txt --
v2 reports additional error positions for jobs1.foo1 and jobs3.fooTest1 (extra positions for pattern/optional constraints); v3 only reports the direct definition position.
-- out/eval/stats --
Leaks:  0
Freed:  19
Reused: 8
Allocs: 11
Retain: 0

Unifications: 19
Conjuncts:    45
Disjuncts:    0

NumCloseIDs: 17
