kwalify 0.1.0 → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,526 @@
1
+ ###
2
+ ### $Rev: 18 $
3
+ ### $Release: 0.2.0 $
4
+ ### copyright(c) 2005 kuwata-lab all rights reserved.
5
+ ###
6
+
7
+ if $0 == __FILE__
8
+ testdir = File.dirname(__FILE__)
9
+ libdir = File.dirname(testdir) + "/lib"
10
+ $LOAD_PATH << libdir << testdir
11
+ require 'test/unit'
12
+ require 'test/unit/ui/console/testrunner'
13
+ require 'kwalify'
14
+ require 'kwalify/util/assert-diff'
15
+ require 'yaml'
16
+ end
17
+
18
+
19
+ class ValidatorTest < Test::Unit::TestCase
20
+
21
+ ## define test methods
22
+ #str = DATA.read() # doesn't work when required by other script
23
+ str = File.read(__FILE__)
24
+ str.gsub!(/.*^__END__$/m, '')
25
+ name_table = {}
26
+ YAML.load_documents(str) do |doc|
27
+ !name_table.key?(doc['name']) or raise "*** test name '#{doc['name']}' is duplicated."
28
+ name_table[doc['name']] = true
29
+ s = <<-END
30
+ def test_#{doc['name']}
31
+ @name = #{doc['name'].dump}
32
+ @schema = #{doc['schema'].dump}
33
+ @valid = #{doc['valid'].dump}
34
+ @invalid = #{doc['invalid'].dump}
35
+ @error = #{doc['error'].dump}
36
+ _test()
37
+ end
38
+ END
39
+ eval s
40
+ end
41
+
42
+ ## execute test
43
+ def _test()
44
+ return if $target && $target != @name
45
+ schema = YAML.load(@schema)
46
+ validator = Kwalify::Validator.new(schema)
47
+ _test_body(validator, @valid, '')
48
+ _test_body(validator, @invalid, @error)
49
+ end
50
+
51
+ def _test_body(validator, input, expected)
52
+ document = YAML.load(input)
53
+ error_list = validator.validate(document)
54
+ actual = ""
55
+ error_list.each do |error|
56
+ actual << "%-20s: [%s] %s\n" % [error.error_symbol.inspect, error.path, error.message]
57
+ end
58
+ if $flag_print
59
+ print actual
60
+ else
61
+ assert_equal_with_diff(expected, actual)
62
+ end
63
+ #return error_list
64
+ end
65
+
66
+ end
67
+
68
+
69
+ #if $0 == __FILE__
70
+ # suite = Test::Unit::TestSuite.new()
71
+ # suite << ValidatorTest.suite()
72
+ # Test::Unit::UI::Console::TestRunner.run(suite)
73
+ #end
74
+
75
+ __END__
76
+ ---
77
+ name: mapping1
78
+ desc: mapping test
79
+ #
80
+ schema: |
81
+ type: map
82
+ required: true
83
+ mapping:
84
+ name:
85
+ type: str
86
+ required: true
87
+ email:
88
+ type: str
89
+ pattern: /@/
90
+ required: yes
91
+ age:
92
+ type: int
93
+ blood:
94
+ type: str
95
+ enum:
96
+ - A
97
+ - B
98
+ - O
99
+ - AB
100
+ birth:
101
+ type: date
102
+ #
103
+ valid: |
104
+ name: foo
105
+ email: foo@mail.com
106
+ age: 20
107
+ blood: AB
108
+ birth: 1985-01-01
109
+ #
110
+ invalid: |
111
+ nam: foo
112
+ email: foo(at)mail.com
113
+ age: twenty
114
+ blood: ab
115
+ birth: Jul 01, 1985
116
+ #
117
+ error: |
118
+ :required_nokey : [/] key 'name:' is required.
119
+ :key_undefined : [/] key 'nam:' is undefined.
120
+ :enum_notexist : [/blood] 'ab': invalid blood value.
121
+ :type_unmatch : [/birth] 'Jul 01, 1985': not a date.
122
+ :type_unmatch : [/age] 'twenty': not a integer.
123
+ :pattern_unmatch : [/email] 'foo(at)mail.com': not matched to pattern /@/.
124
+ #
125
+ ---
126
+ name: sequence1
127
+ desc: sequence test
128
+ #
129
+ schema: |
130
+ type: seq
131
+ required: true
132
+ sequence:
133
+ - type: str
134
+ required: true
135
+ #
136
+ valid: |
137
+ - foo
138
+ - bar
139
+ - baz
140
+ #
141
+ invalid: |
142
+ - foo
143
+ - bar
144
+ -
145
+ - baz
146
+ - 100
147
+ #
148
+ error: |
149
+ :required_novalue : [/2] value required but none.
150
+ :type_unmatch : [/4] '100': not a string.
151
+ #
152
+ ---
153
+ name: nested1
154
+ desc: nest of seq and map
155
+ #
156
+ schema: |
157
+ type: map
158
+ required: true
159
+ mapping:
160
+ address-book:
161
+ type: seq
162
+ required: true
163
+ sequence:
164
+ - type: map
165
+ mapping:
166
+ name:
167
+ type: str
168
+ required: yes
169
+ email:
170
+ type: str
171
+ pattern: /@/
172
+ required: yes
173
+ age:
174
+ type: int
175
+ blood:
176
+ type: str
177
+ enum:
178
+ - A
179
+ - B
180
+ - O
181
+ - AB
182
+ birth:
183
+ type: date
184
+ #
185
+ valid: |
186
+ address-book:
187
+ - name: foo
188
+ email: foo@mail.com
189
+ age: 20
190
+ blood: AB
191
+ birth: 1985-01-01
192
+ - name: bar
193
+ email: foo@mail.com
194
+ #
195
+ invalid: |
196
+ address-book:
197
+ - name: foo
198
+ mail: foo@mail.com
199
+ age: twenty
200
+ blood: ab
201
+ birth: 1985/01/01
202
+ - name: bar
203
+ email: bar(at)mail.com
204
+ #
205
+ error: |
206
+ :required_nokey : [/address-book/0] key 'email:' is required.
207
+ :key_undefined : [/address-book/0] key 'mail:' is undefined.
208
+ :enum_notexist : [/address-book/0/blood] 'ab': invalid blood value.
209
+ :type_unmatch : [/address-book/0/birth] '1985/01/01': not a date.
210
+ :type_unmatch : [/address-book/0/age] 'twenty': not a integer.
211
+ :pattern_unmatch : [/address-book/1/email] 'bar(at)mail.com': not matched to pattern /@/.
212
+ #
213
+ ---
214
+ name: anchor1
215
+ desc: schema with anchor
216
+ #
217
+ schema: |
218
+ type: seq
219
+ required: true
220
+ sequence:
221
+ - type: map
222
+ required: true
223
+ mapping:
224
+ first-name: &name
225
+ type: str
226
+ required: yes
227
+ family-name: *name
228
+ #
229
+ valid: |
230
+ - first-name: foo
231
+ family-name: Foo
232
+ - first-name: bar
233
+ family-name: Bar
234
+ #
235
+ invalid: |
236
+ - first-name: foo
237
+ last-name: Foo
238
+ - first-name: bar
239
+ family-name: 100
240
+ #
241
+ error: |
242
+ :required_nokey : [/0] key 'family-name:' is required.
243
+ :key_undefined : [/0] key 'last-name:' is undefined.
244
+ :type_unmatch : [/1/family-name] '100': not a string.
245
+ #
246
+ ---
247
+ name: anchor2
248
+ desc: schema with anchor 2
249
+ #
250
+ schema: |
251
+ type: map
252
+ required: true
253
+ mapping:
254
+ title: &name
255
+ type: str
256
+ required: true
257
+ address-book:
258
+ type: seq
259
+ required: true
260
+ sequence:
261
+ - type: map
262
+ mapping:
263
+ name: *name
264
+ email:
265
+ type: str
266
+ required: yes
267
+ #
268
+ valid: |
269
+ title: my friends
270
+ address-book:
271
+ - name: foo
272
+ email: foo@mail.com
273
+ - name: bar
274
+ email: bar@mail.com
275
+ #
276
+ invalid: |
277
+ title: my friends
278
+ address-book:
279
+ - name: 100
280
+ email: foo@mail.com
281
+ - first-name: bar
282
+ email: bar@mail.com
283
+ #
284
+ error: |
285
+ :type_unmatch : [/address-book/0/name] '100': not a string.
286
+ :required_nokey : [/address-book/1] key 'name:' is required.
287
+ :key_undefined : [/address-book/1] key 'first-name:' is undefined.
288
+ #
289
+ ---
290
+ name: anchor3
291
+ desc: document with anchor
292
+ #
293
+ schema: |
294
+ type: seq
295
+ sequence:
296
+ - &employee
297
+ type: map
298
+ mapping:
299
+ name:
300
+ type: str
301
+ post:
302
+ type: str
303
+ enum:
304
+ - exective
305
+ - manager
306
+ - clerk
307
+ supervisor: *employee
308
+ #
309
+ valid: |
310
+ - &foo
311
+ name: foo
312
+ post: exective
313
+ - &bar
314
+ name: bar
315
+ post: manager
316
+ supervisor: *foo
317
+ - &baz
318
+ name: baz
319
+ post: clerk
320
+ supervisor: *bar
321
+ - &zak
322
+ name: zak
323
+ post: clerk
324
+ supervisor: *bar
325
+ #
326
+ invalid: |
327
+ - &foo
328
+ name: 100
329
+ post: exective
330
+ supervisor: *foo
331
+ - &bar
332
+ name: foo
333
+ post: worker
334
+ supervisor: *foo
335
+ #
336
+ error: |
337
+ :type_unmatch : [/0/name] '100': not a string.
338
+ :enum_notexist : [/1/post] 'worker': invalid post value.
339
+ #
340
+ ---
341
+ name: range1
342
+ desc: range test && bug#?????
343
+ #
344
+ schema: |
345
+ type: map
346
+ mapping:
347
+ "max-only":
348
+ type: seq
349
+ sequence:
350
+ - type: number
351
+ required: yes
352
+ range: { max: 100 }
353
+ "min-only":
354
+ type: seq
355
+ sequence:
356
+ - type: number
357
+ required: yes
358
+ range: { min: 10.0 }
359
+ "max-and-min":
360
+ type: seq
361
+ sequence:
362
+ - type: number
363
+ required: yes
364
+ range: { max: 100.0, min: 10.0 }
365
+ #
366
+ valid: |
367
+ max-only:
368
+ - 100
369
+ - 100.0
370
+ min-only:
371
+ - 10
372
+ - 10.0
373
+ max-and-min:
374
+ - 100
375
+ - 10
376
+ - 100.0
377
+ - 10.0
378
+ #
379
+ invalid: |
380
+ max-only:
381
+ - 101
382
+ - 100.1
383
+ min-only:
384
+ - 9
385
+ - 9.99
386
+ max-and-min:
387
+ - 101
388
+ - 100.1
389
+ - 9
390
+ - 9.99
391
+ #
392
+ error: |
393
+ :range_toosmall : [/min-only/0] '9': too small (< min 10.0).
394
+ :range_toosmall : [/min-only/1] '9.99': too small (< min 10.0).
395
+ :range_toolarge : [/max-and-min/0] '101': too large (> max 100.0).
396
+ :range_toolarge : [/max-and-min/1] '100.1': too large (> max 100.0).
397
+ :range_toosmall : [/max-and-min/2] '9': too small (< min 10.0).
398
+ :range_toosmall : [/max-and-min/3] '9.99': too small (< min 10.0).
399
+ :range_toolarge : [/max-only/0] '101': too large (> max 100).
400
+ :range_toolarge : [/max-only/1] '100.1': too large (> max 100).
401
+ #
402
+ ---
403
+ name: length1
404
+ desc: length test
405
+ #
406
+ schema: |
407
+ type: map
408
+ mapping:
409
+ "max-only":
410
+ type: seq
411
+ sequence:
412
+ - type: text
413
+ length: { max: 8 }
414
+ "min-only":
415
+ type: seq
416
+ sequence:
417
+ - type: text
418
+ length: { min: 4 }
419
+ "max-and-min":
420
+ type: seq
421
+ sequence:
422
+ - type: text
423
+ length: { max: 8, min: 4 }
424
+ #
425
+ valid: |
426
+ max-only:
427
+ - hogehoge
428
+ - 12345678
429
+ - a
430
+ -
431
+ min-only:
432
+ - hoge
433
+ - 1234
434
+ - hogehogehogehogehoge
435
+ max-and-min:
436
+ - hogehoge
437
+ - 12345678
438
+ - hoge
439
+ - 1234
440
+ #
441
+ invalid: |
442
+ max-only:
443
+ - hogehoge!
444
+ min-only:
445
+ - foo
446
+ -
447
+ max-and-min:
448
+ - foobarbaz
449
+ - foo
450
+ #
451
+ error: |
452
+ :length_tooshort : [/min-only/0] 'foo': too short (length 3 < min 4).
453
+ :length_toolong : [/max-and-min/0] 'foobarbaz': too long (length 9 > max 8).
454
+ :length_tooshort : [/max-and-min/1] 'foo': too short (length 3 < min 4).
455
+ :length_toolong : [/max-only/0] 'hogehoge!': too long (length 9 > max 8).
456
+ #
457
+ ---
458
+ name: assert1
459
+ desc: assert test
460
+ #
461
+ schema: |
462
+ type: seq
463
+ sequence:
464
+ - type: map
465
+ mapping:
466
+ "less-than":
467
+ type: number
468
+ assert: val < 8
469
+ "more-than":
470
+ type: number
471
+ assert: 3 < val
472
+ "between":
473
+ type: number
474
+ assert: 3 < val && val < 8
475
+ "except":
476
+ type: number
477
+ assert: val < 3 || 8 < val
478
+ #
479
+ valid: |
480
+ - less-than: 5
481
+ - more-than: 5
482
+ - between: 5
483
+ - except: 0
484
+ #
485
+ invalid: |
486
+ - less-than: 8
487
+ - more-than: 3
488
+ - between: 2.9
489
+ - except: 3.1
490
+ #
491
+ error: |
492
+ :assert_failed : [/0/less-than] '8': assertion expression failed (val < 8).
493
+ :assert_failed : [/1/more-than] '3': assertion expression failed (3 < val).
494
+ :assert_failed : [/2/between] '2.9': assertion expression failed (3 < val && val < 8).
495
+ :assert_failed : [/3/except] '3.1': assertion expression failed (val < 3 || 8 < val).
496
+ #
497
+ ---
498
+ name: deftype1
499
+ desc: default type test
500
+ #
501
+ schema: |
502
+ type: seq
503
+ sequence:
504
+ - type: map
505
+ mapping:
506
+ "name":
507
+ "email":
508
+ #
509
+ valid: |
510
+ - name: foo
511
+ email: foo@mail.com
512
+ - name: bar
513
+ - email: baz@mail.com
514
+ #
515
+ invalid: |
516
+ - name: 123
517
+ email: true
518
+ - name: 3.14
519
+ - email: 2004-01-01
520
+ #
521
+ error: |
522
+ :type_unmatch : [/0/name] '123': not a string.
523
+ :type_unmatch : [/0/email] 'true': not a string.
524
+ :type_unmatch : [/1/name] '3.14': not a string.
525
+ :type_unmatch : [/2/email] '2004-01-01': not a string.
526
+ #