Skip to content

Commit 06be133

Browse files
committed
wip
1 parent 15a84c4 commit 06be133

File tree

1 file changed

+293
-0
lines changed

1 file changed

+293
-0
lines changed
Lines changed: 293 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,293 @@
1+
package json.java21.jtd;
2+
3+
import jdk.sandbox.java.util.json.Json;
4+
import jdk.sandbox.java.util.json.JsonValue;
5+
import org.junit.jupiter.api.Test;
6+
7+
import static org.assertj.core.api.Assertions.assertThat;
8+
9+
/// RFC 8927 compliance tests for failing JTD specification cases
10+
/// These are the exact test cases that were failing in JtdSpecIT
11+
/// with explicit multiline strings for schema and JSON documents
12+
public class TestRfc8927Compliance extends JtdTestBase {
13+
14+
/// Test ref schema with nested definitions
15+
/// "ref schema - nested ref" from JTD specification test suite
16+
/// Should resolve nested ref "bar" inside definition "foo"
17+
@Test
18+
public void testRefSchemaNestedRef() throws Exception {
19+
// Schema with nested ref: foo references bar, bar is empty schema
20+
JsonValue schema = Json.parse("""
21+
{
22+
"definitions": {
23+
"foo": {
24+
"ref": "bar"
25+
},
26+
"bar": {}
27+
},
28+
"ref": "foo"
29+
}
30+
""");
31+
32+
JsonValue instance = Json.parse("true");
33+
34+
LOG.info(() -> "Testing ref schema - nested ref");
35+
LOG.fine(() -> "Schema: " + schema);
36+
LOG.fine(() -> "Instance: " + instance);
37+
38+
Jtd validator = new Jtd();
39+
Jtd.Result result = validator.validate(schema, instance);
40+
41+
LOG.fine(() -> "Validation result: " + (result.isValid() ? "VALID" : "INVALID"));
42+
if (!result.isValid()) {
43+
LOG.severe(() -> "ERRORS: " + result.errors());
44+
}
45+
46+
// This should be valid according to RFC 8927
47+
assertThat(result.isValid())
48+
.as("Nested ref should resolve correctly")
49+
.isTrue();
50+
}
51+
52+
/// Test ref schema with recursive definitions
53+
/// "ref schema - recursive schema, ok" from JTD specification test suite
54+
/// Should handle recursive ref to self in elements schema
55+
@Test
56+
public void testRefSchemaRecursive() throws Exception {
57+
// Schema with recursive ref: root references itself in elements
58+
JsonValue schema = Json.parse("""
59+
{
60+
"definitions": {
61+
"root": {
62+
"elements": {
63+
"ref": "root"
64+
}
65+
}
66+
},
67+
"ref": "root"
68+
}
69+
""");
70+
71+
JsonValue instance = Json.parse("[]");
72+
73+
LOG.info(() -> "Testing ref schema - recursive schema, ok");
74+
LOG.fine(() -> "Schema: " + schema);
75+
LOG.fine(() -> "Instance: " + instance);
76+
77+
Jtd validator = new Jtd();
78+
Jtd.Result result = validator.validate(schema, instance);
79+
80+
LOG.fine(() -> "Validation result: " + (result.isValid() ? "VALID" : "INVALID"));
81+
if (!result.isValid()) {
82+
LOG.severe(() -> "ERRORS: " + result.errors());
83+
}
84+
85+
// This should be valid according to RFC 8927
86+
assertThat(result.isValid())
87+
.as("Recursive ref should resolve correctly")
88+
.isTrue();
89+
}
90+
91+
/// Test timestamp with leap second
92+
/// "timestamp type schema - 1990-12-31T23:59:60Z" from JTD specification test suite
93+
/// Should accept valid RFC 3339 timestamp with leap second
94+
@Test
95+
public void testTimestampWithLeapSecond() throws Exception {
96+
JsonValue schema = Json.parse("""
97+
{
98+
"type": "timestamp"
99+
}
100+
""");
101+
102+
JsonValue instance = Json.parse("\"1990-12-31T23:59:60Z\"");
103+
104+
LOG.info(() -> "Testing timestamp type schema - 1990-12-31T23:59:60Z");
105+
LOG.fine(() -> "Schema: " + schema);
106+
LOG.fine(() -> "Instance: " + instance);
107+
108+
Jtd validator = new Jtd();
109+
Jtd.Result result = validator.validate(schema, instance);
110+
111+
LOG.fine(() -> "Validation result: " + (result.isValid() ? "VALID" : "INVALID"));
112+
if (!result.isValid()) {
113+
LOG.severe(() -> "ERRORS: " + result.errors());
114+
}
115+
116+
// This should be valid according to RFC 8927 (leap second support)
117+
assertThat(result.isValid())
118+
.as("Timestamp with leap second should be valid RFC 3339")
119+
.isTrue();
120+
}
121+
122+
/// Test timestamp with timezone offset
123+
/// "timestamp type schema - 1990-12-31T15:59:60-08:00" from JTD specification test suite
124+
/// Should accept valid RFC 3339 timestamp with timezone offset
125+
@Test
126+
public void testTimestampWithTimezone() throws Exception {
127+
JsonValue schema = Json.parse("""
128+
{
129+
"type": "timestamp"
130+
}
131+
""");
132+
133+
JsonValue instance = Json.parse("\"1990-12-31T15:59:60-08:00\"");
134+
135+
LOG.info(() -> "Testing timestamp type schema - 1990-12-31T15:59:60-08:00");
136+
LOG.fine(() -> "Schema: " + schema);
137+
LOG.fine(() -> "Instance: " + instance);
138+
139+
Jtd validator = new Jtd();
140+
Jtd.Result result = validator.validate(schema, instance);
141+
142+
LOG.fine(() -> "Validation result: " + (result.isValid() ? "VALID" : "INVALID"));
143+
if (!result.isValid()) {
144+
LOG.severe(() -> "ERRORS: " + result.errors());
145+
}
146+
147+
// This should be valid according to RFC 8927 (timezone support)
148+
assertThat(result.isValid())
149+
.as("Timestamp with timezone offset should be valid RFC 3339")
150+
.isTrue();
151+
}
152+
153+
/// Test strict properties validation
154+
/// "strict properties - bad additional property" from JTD specification test suite
155+
/// Should reject object with additional property not in schema
156+
@Test
157+
public void testStrictPropertiesBadAdditionalProperty() throws Exception {
158+
JsonValue schema = Json.parse("""
159+
{
160+
"properties": {
161+
"foo": {
162+
"type": "string"
163+
}
164+
}
165+
}
166+
""");
167+
168+
JsonValue instance = Json.parse("""
169+
{
170+
"foo": "foo",
171+
"bar": "bar"
172+
}
173+
""");
174+
175+
LOG.info(() -> "Testing strict properties - bad additional property");
176+
LOG.fine(() -> "Schema: " + schema);
177+
LOG.fine(() -> "Instance: " + instance);
178+
179+
Jtd validator = new Jtd();
180+
Jtd.Result result = validator.validate(schema, instance);
181+
182+
LOG.fine(() -> "Validation result: " + (result.isValid() ? "VALID" : "INVALID"));
183+
if (!result.isValid()) {
184+
LOG.fine(() -> "ERRORS: " + result.errors());
185+
}
186+
187+
// This should be invalid according to RFC 8927 (strict by default)
188+
assertThat(result.isValid())
189+
.as("Object with additional property should be rejected in strict mode")
190+
.isFalse();
191+
192+
// Should have error about the additional property
193+
assertThat(result.errors())
194+
.isNotEmpty()
195+
.anySatisfy(error -> assertThat(error).contains("bar"));
196+
}
197+
198+
/// Test strict optional properties validation
199+
/// "strict optionalProperties - bad additional property" from JTD specification test suite
200+
/// Should reject object with additional property not in optionalProperties
201+
@Test
202+
public void testStrictOptionalPropertiesBadAdditionalProperty() throws Exception {
203+
JsonValue schema = Json.parse("""
204+
{
205+
"optionalProperties": {
206+
"foo": {
207+
"type": "string"
208+
}
209+
}
210+
}
211+
""");
212+
213+
JsonValue instance = Json.parse("""
214+
{
215+
"foo": "foo",
216+
"bar": "bar"
217+
}
218+
""");
219+
220+
LOG.info(() -> "Testing strict optionalProperties - bad additional property");
221+
LOG.fine(() -> "Schema: " + schema);
222+
LOG.fine(() -> "Instance: " + instance);
223+
224+
Jtd validator = new Jtd();
225+
Jtd.Result result = validator.validate(schema, instance);
226+
227+
LOG.fine(() -> "Validation result: " + (result.isValid() ? "VALID" : "INVALID"));
228+
if (!result.isValid()) {
229+
LOG.fine(() -> "ERRORS: " + result.errors());
230+
}
231+
232+
// This should be invalid according to RFC 8927 (strict by default)
233+
assertThat(result.isValid())
234+
.as("Object with additional property should be rejected in strict mode")
235+
.isFalse();
236+
237+
// Should have error about the additional property
238+
assertThat(result.errors())
239+
.isNotEmpty()
240+
.anySatisfy(error -> assertThat(error).contains("bar"));
241+
}
242+
243+
/// Test strict mixed properties validation
244+
/// "strict mixed properties and optionalProperties - bad additional property" from JTD specification test suite
245+
/// Should reject object with additional property not in properties or optionalProperties
246+
@Test
247+
public void testStrictMixedPropertiesBadAdditionalProperty() throws Exception {
248+
JsonValue schema = Json.parse("""
249+
{
250+
"properties": {
251+
"foo": {
252+
"type": "string"
253+
}
254+
},
255+
"optionalProperties": {
256+
"bar": {
257+
"type": "string"
258+
}
259+
}
260+
}
261+
""");
262+
263+
JsonValue instance = Json.parse("""
264+
{
265+
"foo": "foo",
266+
"bar": "bar",
267+
"baz": "baz"
268+
}
269+
""");
270+
271+
LOG.info(() -> "Testing strict mixed properties and optionalProperties - bad additional property");
272+
LOG.fine(() -> "Schema: " + schema);
273+
LOG.fine(() -> "Instance: " + instance);
274+
275+
Jtd validator = new Jtd();
276+
Jtd.Result result = validator.validate(schema, instance);
277+
278+
LOG.fine(() -> "Validation result: " + (result.isValid() ? "VALID" : "INVALID"));
279+
if (!result.isValid()) {
280+
LOG.fine(() -> "ERRORS: " + result.errors());
281+
}
282+
283+
// This should be invalid according to RFC 8927 (strict by default)
284+
assertThat(result.isValid())
285+
.as("Object with additional property should be rejected in strict mode")
286+
.isFalse();
287+
288+
// Should have error about the additional property
289+
assertThat(result.errors())
290+
.isNotEmpty()
291+
.anySatisfy(error -> assertThat(error).contains("baz"));
292+
}
293+
}

0 commit comments

Comments
 (0)