PageRenderTime 54ms CodeModel.GetById 15ms RepoModel.GetById 1ms app.codeStats 0ms

/test/rexml/test_validation_rng.rb

http://github.com/ruby/ruby
Ruby | 793 lines | 695 code | 93 blank | 5 comment | 0 complexity | 6845f174c93bd6f891419c73fa1d7a71 MD5 | raw file
Possible License(s): GPL-2.0, BSD-3-Clause, AGPL-3.0
  1. # frozen_string_literal: false
  2. require "test/unit/testcase"
  3. require "rexml/document"
  4. require "rexml/validation/relaxng"
  5. module REXMLTests
  6. class RNGValidation < Test::Unit::TestCase
  7. include REXML
  8. def test_validate
  9. rng = %q{
  10. <?xml version="1.0" encoding="UTF-8"?>
  11. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  12. <element name="B">
  13. <element name="C">
  14. <attribute name="X"/>
  15. <zeroOrMore>
  16. <element name="E">
  17. <empty/>
  18. </element>
  19. </zeroOrMore>
  20. </element>
  21. <element name="D">
  22. <empty/>
  23. </element>
  24. </element>
  25. </element>
  26. }
  27. validator = REXML::Validation::RelaxNG.new( rng )
  28. no_error( validator, %q{<A><B><C X="x"><E/><E/></C><D/></B></A>} )
  29. error( validator, %q{<A><B><D/><C X="x"/></B></A>} )
  30. end
  31. def test_sequence
  32. rng = %q{
  33. <?xml version="1.0" encoding="UTF-8"?>
  34. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  35. <element name="B">
  36. <element name="C">
  37. <empty/>
  38. </element>
  39. <element name="D">
  40. <empty/>
  41. </element>
  42. </element>
  43. </element>
  44. }
  45. validator = REXML::Validation::RelaxNG.new( rng )
  46. error( validator, %q{<A><B><C/><C/><D/></B></A>} )
  47. error( validator, %q{<A><B><D/><C/></B></A>} )
  48. error( validator, %q{<A><C/><D/></A>} )
  49. no_error( validator, %q{<A><B><C/><D/></B></A>} )
  50. end
  51. def test_choice
  52. rng = %q{
  53. <?xml version="1.0" encoding="UTF-8"?>
  54. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  55. <element name="B">
  56. <choice>
  57. <element name="C">
  58. <empty/>
  59. </element>
  60. <element name="D">
  61. <empty/>
  62. </element>
  63. </choice>
  64. </element>
  65. </element>
  66. }
  67. validator = REXML::Validation::RelaxNG.new( rng )
  68. error( validator, %q{<A><B><C/><D/></B></A>} )
  69. no_error( validator, %q{<A><B><D/></B></A>} )
  70. no_error( validator, %q{<A><B><C/></B></A>} )
  71. end
  72. def test_optional
  73. rng = %q{
  74. <?xml version="1.0" encoding="UTF-8"?>
  75. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  76. <element name="B">
  77. <optional>
  78. <element name="C">
  79. <empty/>
  80. </element>
  81. </optional>
  82. </element>
  83. </element>
  84. }
  85. validator = REXML::Validation::RelaxNG.new( rng )
  86. no_error( validator, %q{<A><B/></A>} )
  87. no_error( validator, %q{<A><B><C/></B></A>} )
  88. error( validator, %q{<A><B><D/></B></A>} )
  89. error( validator, %q{<A><B><C/><C/></B></A>} )
  90. end
  91. def test_zero_or_more
  92. rng = %q{
  93. <?xml version="1.0" encoding="UTF-8"?>
  94. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  95. <element name="B">
  96. <zeroOrMore>
  97. <element name="C">
  98. <empty/>
  99. </element>
  100. </zeroOrMore>
  101. </element>
  102. </element>
  103. }
  104. validator = REXML::Validation::RelaxNG.new( rng )
  105. no_error( validator, %q{<A><B/></A>} )
  106. no_error( validator, %q{<A><B><C/></B></A>} )
  107. no_error( validator, %q{<A><B><C/><C/><C/></B></A>} )
  108. error( validator, %q{<A><B><D/></B></A>} )
  109. error( validator, %q{<A></A>} )
  110. rng = %q{
  111. <?xml version="1.0" encoding="UTF-8"?>
  112. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  113. <element name="B">
  114. <zeroOrMore>
  115. <element name="C">
  116. <empty/>
  117. </element>
  118. <element name="D">
  119. <empty/>
  120. </element>
  121. </zeroOrMore>
  122. </element>
  123. </element>
  124. }
  125. validator = REXML::Validation::RelaxNG.new( rng )
  126. no_error( validator, %q{<A><B/></A>} )
  127. no_error( validator, %q{<A><B><C/><D/></B></A>} )
  128. no_error( validator, %q{<A><B><C/><D/><C/><D/></B></A>} )
  129. error( validator, %q{<A><B><D/></B></A>} )
  130. end
  131. def test_one_or_more
  132. rng = %q{
  133. <?xml version="1.0" encoding="UTF-8"?>
  134. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  135. <element name="B">
  136. <oneOrMore>
  137. <element name="C">
  138. <empty/>
  139. </element>
  140. </oneOrMore>
  141. </element>
  142. </element>
  143. }
  144. validator = REXML::Validation::RelaxNG.new( rng )
  145. error( validator, %q{<A><B/></A>} )
  146. no_error( validator, %q{<A><B><C/></B></A>} )
  147. no_error( validator, %q{<A><B><C/><C/><C/></B></A>} )
  148. error( validator, %q{<A><B><D/></B></A>} )
  149. error( validator, %q{<A></A>} )
  150. end
  151. def test_attribute
  152. rng = %q{
  153. <?xml version="1.0" encoding="UTF-8"?>
  154. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  155. <attribute name="X"/>
  156. <attribute name="Y"/>
  157. </element>
  158. }
  159. validator = REXML::Validation::RelaxNG.new( rng )
  160. error( validator, %q{<A><B/></A>} )
  161. error( validator, %q{<A/>} )
  162. error( validator, %q{<A X=""/>} )
  163. no_error( validator, %q{<A X="1" Y="1"/>} )
  164. end
  165. def test_choice_attributes
  166. rng = %q{
  167. <?xml version="1.0" encoding="UTF-8"?>
  168. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  169. <choice>
  170. <attribute name="X"/>
  171. <attribute name="Y"/>
  172. </choice>
  173. </element>
  174. }
  175. validator = REXML::Validation::RelaxNG.new( rng )
  176. error( validator, %q{<A X="1" Y="1"/>} )
  177. error( validator, %q{<A/>} )
  178. no_error( validator, %q{<A X="1"/>})
  179. no_error( validator, %q{<A Y="1"/>} )
  180. end
  181. def test_choice_attribute_element
  182. rng = %q{
  183. <?xml version="1.0" encoding="UTF-8"?>
  184. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  185. <choice>
  186. <attribute name="X"/>
  187. <element name="B"/>
  188. </choice>
  189. </element>
  190. }
  191. validator = REXML::Validation::RelaxNG.new( rng )
  192. error( validator, %q{<A X="1"><B/></A>} )
  193. error( validator, %q{<A/>} )
  194. no_error( validator, %q{<A X="1"/>})
  195. no_error( validator, %q{<A><B/></A>} )
  196. end
  197. def test_empty
  198. rng = %q{
  199. <?xml version="1.0" encoding="UTF-8"?>
  200. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  201. <empty/>
  202. </element>
  203. }
  204. validator = REXML::Validation::RelaxNG.new( rng )
  205. error( validator, %q{<A><B/></A>} )
  206. error( validator, %q{<A>Text</A>} )
  207. no_error( validator, %q{<A/>})
  208. end
  209. def test_text_val
  210. rng = %q{
  211. <?xml version="1.0" encoding="UTF-8"?>
  212. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  213. <text/>
  214. </element>
  215. }
  216. validator = REXML::Validation::RelaxNG.new( rng )
  217. error( validator, %q{<A><B/></A>} )
  218. no_error( validator, %q{<A>Text</A>} )
  219. error( validator, %q{<A/>})
  220. end
  221. def test_choice_text
  222. rng = %q{
  223. <?xml version="1.0" encoding="UTF-8"?>
  224. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  225. <choice>
  226. <element name="B"/>
  227. <text/>
  228. </choice>
  229. </element>
  230. }
  231. validator = REXML::Validation::RelaxNG.new( rng )
  232. error( validator, %q{<A><B/>Text</A>} )
  233. error( validator, %q{<A>Text<B/></A>} )
  234. no_error( validator, %q{<A>Text</A>} )
  235. no_error( validator, %q{<A><B/></A>} )
  236. end
  237. def test_group
  238. rng = %q{
  239. <?xml version="1.0" encoding="UTF-8"?>
  240. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  241. <choice>
  242. <element name="B"/>
  243. <group>
  244. <element name="C"/>
  245. <element name="D"/>
  246. </group>
  247. </choice>
  248. </element>
  249. }
  250. validator = REXML::Validation::RelaxNG.new( rng )
  251. error( validator, %q{<A><B/><C/></A>} )
  252. error( validator, %q{<A><C/></A>} )
  253. no_error( validator, %q{<A><B/></A>} )
  254. no_error( validator, %q{<A><C/><D/></A>} )
  255. rng = %q{
  256. <?xml version="1.0" encoding="UTF-8"?>
  257. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  258. <element name="B"/>
  259. <group>
  260. <element name="C"/>
  261. <element name="D"/>
  262. </group>
  263. </element>
  264. }
  265. validator = REXML::Validation::RelaxNG.new( rng )
  266. error( validator, %q{<A><B/><C/></A>} )
  267. error( validator, %q{<A><B/><D/></A>} )
  268. error( validator, %q{<A><B/></A>} )
  269. no_error( validator, %q{<A><B/><C/><D/></A>} )
  270. end
  271. def test_value
  272. # Values as text nodes
  273. rng = %q{
  274. <?xml version="1.0" encoding="UTF-8"?>
  275. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  276. <element name="B">
  277. <value>VaLuE</value>
  278. </element>
  279. </element>
  280. }
  281. validator = REXML::Validation::RelaxNG.new( rng )
  282. error( validator, %q{<A><B>X</B></A>} )
  283. error( validator, %q{<A><B/></A>} )
  284. no_error( validator, %q{<A><B>VaLuE</B></A>} )
  285. # Values as text nodes, via choice
  286. rng = %q{
  287. <?xml version="1.0" encoding="UTF-8"?>
  288. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  289. <element name="B">
  290. <choice>
  291. <value>Option 1</value>
  292. <value>Option 2</value>
  293. </choice>
  294. </element>
  295. </element>
  296. }
  297. validator = REXML::Validation::RelaxNG.new( rng )
  298. error( validator, %q{<A><B/></A>} )
  299. error( validator, %q{<A><B>XYZ</B></A>} )
  300. no_error( validator, %q{<A><B>Option 1</B></A>} )
  301. no_error( validator, %q{<A><B>Option 2</B></A>} )
  302. # Attribute values
  303. rng = %q{
  304. <?xml version="1.0" encoding="UTF-8"?>
  305. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  306. <attribute name="B">
  307. <value>VaLuE</value>
  308. </attribute>
  309. </element>
  310. }
  311. validator = REXML::Validation::RelaxNG.new( rng )
  312. error( validator, %q{<A/>} )
  313. error( validator, %q{<A B=""/>} )
  314. error( validator, %q{<A B="Lala"/>} )
  315. no_error( validator, %q{<A B="VaLuE"/>} )
  316. # Attribute values via choice
  317. rng = %q{
  318. <?xml version="1.0" encoding="UTF-8"?>
  319. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  320. <attribute name="B">
  321. <choice>
  322. <value>Option 1</value>
  323. <value>Option 2</value>
  324. </choice>
  325. </attribute>
  326. </element>
  327. }
  328. validator = REXML::Validation::RelaxNG.new( rng )
  329. error( validator, %q{<A B=""/>} )
  330. error( validator, %q{<A B="Value"/>} )
  331. no_error( validator, %q{<A B="Option 1"></A>} )
  332. no_error( validator, %q{<A B="Option 2"/>} )
  333. end
  334. def test_interleave
  335. rng = %q{
  336. <?xml version="1.0" encoding="UTF-8"?>
  337. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  338. <element name="B">
  339. <interleave>
  340. <element name="C"/>
  341. <element name="D"/>
  342. <element name="E"/>
  343. </interleave>
  344. </element>
  345. </element>
  346. }
  347. validator = REXML::Validation::RelaxNG.new( rng )
  348. error( validator, %q{<A><B><C/></B></A>} )
  349. error( validator, %q{<A><B><C/><D/><C/></B></A>} )
  350. no_error( validator, %q{<A><B><C/><D/><E/></B></A>} )
  351. no_error( validator, %q{<A><B><E/><D/><C/></B></A>} )
  352. no_error( validator, %q{<A><B><D/><C/><E/></B></A>} )
  353. no_error( validator, %q{<A><B><E/><C/><D/></B></A>} )
  354. error( validator, %q{<A><B><E/><C/><D/><C/></B></A>} )
  355. end
  356. def test_mixed
  357. rng = %q{
  358. <?xml version="1.0" encoding="UTF-8"?>
  359. <element name="A" xmlns="http://relaxng.org/ns/structure/1.0">
  360. <element name="B">
  361. <mixed>
  362. <element name="D"/>
  363. </mixed>
  364. </element>
  365. </element>
  366. }
  367. validator = REXML::Validation::RelaxNG.new( rng )
  368. no_error( validator, %q{<A><B>Text<D/></B></A>} )
  369. no_error( validator, %q{<A><B><D/>Text</B></A>} )
  370. end
  371. def test_ref_sequence
  372. rng = %q{
  373. <?xml version="1.0" encoding="UTF-8"?>
  374. <grammar xmlns="http://relaxng.org/ns/structure/1.0">
  375. <start>
  376. <element name="A">
  377. <ref name="B"/>
  378. <ref name="B"/>
  379. </element>
  380. </start>
  381. <define name="B">
  382. <element name="B">
  383. <attribute name="X"/>
  384. </element>
  385. </define>
  386. </grammar>
  387. }
  388. validator = REXML::Validation::RelaxNG.new( rng )
  389. no_error( validator, %q{<A><B X=''/><B X=''/></A>} )
  390. error( validator, %q{<A><B X=''/></A>} )
  391. end
  392. def test_ref_choice
  393. rng = %q{
  394. <?xml version="1.0" encoding="UTF-8"?>
  395. <grammar xmlns="http://relaxng.org/ns/structure/1.0">
  396. <start>
  397. <element name="A">
  398. <choice>
  399. <ref name="B"/>
  400. </choice>
  401. </element>
  402. </start>
  403. <define name="B">
  404. <element name="B"/>
  405. <element name="C"/>
  406. </define>
  407. </grammar>
  408. }
  409. validator = REXML::Validation::RelaxNG.new( rng )
  410. error( validator, %q{<A><D/></A>} )
  411. error( validator, %q{<A><B/><C/></A>} )
  412. no_error( validator, %q{<A><B/></A>} )
  413. no_error( validator, %q{<A><C/></A>} )
  414. rng = %q{
  415. <?xml version="1.0" encoding="UTF-8"?>
  416. <grammar xmlns="http://relaxng.org/ns/structure/1.0">
  417. <start>
  418. <element name="A">
  419. <ref name="B"/>
  420. </element>
  421. </start>
  422. <define name="B">
  423. <choice>
  424. <element name="B"/>
  425. <element name="C"/>
  426. </choice>
  427. </define>
  428. </grammar>
  429. }
  430. validator = REXML::Validation::RelaxNG.new( rng )
  431. error( validator, %q{<A><D/></A>} )
  432. error( validator, %q{<A><B/><C/></A>} )
  433. no_error( validator, %q{<A><B/></A>} )
  434. no_error( validator, %q{<A><C/></A>} )
  435. rng = %q{
  436. <?xml version="1.0" encoding="UTF-8"?>
  437. <grammar xmlns="http://relaxng.org/ns/structure/1.0">
  438. <start>
  439. <element name="A">
  440. <choice>
  441. <ref name="B"/>
  442. <element name="D"/>
  443. </choice>
  444. </element>
  445. </start>
  446. <define name="B">
  447. <element name="B"/>
  448. <element name="C"/>
  449. </define>
  450. </grammar>
  451. }
  452. validator = REXML::Validation::RelaxNG.new( rng )
  453. error( validator, %q{<A><B/><C/></A>} )
  454. no_error( validator, %q{<A><B/></A>} )
  455. no_error( validator, %q{<A><C/></A>} )
  456. no_error( validator, %q{<A><D/></A>} )
  457. end
  458. def test_ref_zero_plus
  459. rng = %q{
  460. <?xml version="1.0" encoding="UTF-8"?>
  461. <grammar xmlns="http://relaxng.org/ns/structure/1.0">
  462. <start>
  463. <element name="A">
  464. <zeroOrMore>
  465. <ref name="B"/>
  466. </zeroOrMore>
  467. </element>
  468. </start>
  469. <define name="B">
  470. <element name="B">
  471. <attribute name="X"/>
  472. </element>
  473. </define>
  474. </grammar>
  475. }
  476. validator = REXML::Validation::RelaxNG.new( rng )
  477. error( validator, %q{<A><B/></A>} )
  478. no_error( validator, %q{<A/>} )
  479. no_error( validator, %q{<A><B X=''/></A>} )
  480. no_error( validator, %q{<A><B X=''/><B X=''/><B X=''/></A>} )
  481. rng = %q{
  482. <?xml version="1.0" encoding="UTF-8"?>
  483. <grammar xmlns="http://relaxng.org/ns/structure/1.0">
  484. <start>
  485. <element name="A">
  486. <ref name="B"/>
  487. </element>
  488. </start>
  489. <define name="B">
  490. <zeroOrMore>
  491. <element name="B">
  492. <attribute name="X"/>
  493. </element>
  494. </zeroOrMore>
  495. </define>
  496. </grammar>
  497. }
  498. validator = REXML::Validation::RelaxNG.new( rng )
  499. error( validator, %q{<A><B/></A>} )
  500. no_error( validator, %q{<A/>} )
  501. no_error( validator, %q{<A><B X=''/></A>} )
  502. no_error( validator, %q{<A><B X=''/><B X=''/><B X=''/></A>} )
  503. end
  504. def test_ref_one_plus
  505. rng = %q{
  506. <?xml version="1.0" encoding="UTF-8"?>
  507. <grammar xmlns="http://relaxng.org/ns/structure/1.0">
  508. <start>
  509. <element name="A">
  510. <oneOrMore>
  511. <ref name="B"/>
  512. </oneOrMore>
  513. </element>
  514. </start>
  515. <define name="B">
  516. <element name="B">
  517. <attribute name="X"/>
  518. </element>
  519. </define>
  520. </grammar>
  521. }
  522. validator = REXML::Validation::RelaxNG.new( rng )
  523. error( validator, %q{<A><B/></A>} )
  524. error( validator, %q{<A/>} )
  525. no_error( validator, %q{<A><B X=''/></A>} )
  526. no_error( validator, %q{<A><B X=''/><B X=''/><B X=''/></A>} )
  527. rng = %q{
  528. <?xml version="1.0" encoding="UTF-8"?>
  529. <grammar xmlns="http://relaxng.org/ns/structure/1.0">
  530. <start>
  531. <element name="A">
  532. <ref name="B"/>
  533. </element>
  534. </start>
  535. <define name="B">
  536. <oneOrMore>
  537. <element name="B">
  538. <attribute name="X"/>
  539. </element>
  540. </oneOrMore>
  541. </define>
  542. </grammar>
  543. }
  544. validator = REXML::Validation::RelaxNG.new( rng )
  545. error( validator, %q{<A><B/></A>} )
  546. error( validator, %q{<A/>} )
  547. no_error( validator, %q{<A><B X=''/></A>} )
  548. no_error( validator, %q{<A><B X=''/><B X=''/><B X=''/></A>} )
  549. end
  550. def test_ref_interleave
  551. rng = %q{
  552. <?xml version="1.0" encoding="UTF-8"?>
  553. <grammar xmlns="http://relaxng.org/ns/structure/1.0">
  554. <start>
  555. <element name="A">
  556. <interleave>
  557. <ref name="B"/>
  558. </interleave>
  559. </element>
  560. </start>
  561. <define name="B">
  562. <element name="B"/>
  563. <element name="C"/>
  564. </define>
  565. </grammar>
  566. }
  567. validator = REXML::Validation::RelaxNG.new( rng )
  568. error( validator, %q{<A><B/></A>} )
  569. error( validator, %q{<A><C/></A>} )
  570. error( validator, %q{<A><C/><C/></A>} )
  571. no_error( validator, %q{<A><B/><C/></A>} )
  572. no_error( validator, %q{<A><C/><B/></A>} )
  573. rng = %q{
  574. <?xml version="1.0" encoding="UTF-8"?>
  575. <grammar xmlns="http://relaxng.org/ns/structure/1.0">
  576. <start>
  577. <element name="A">
  578. <ref name="B"/>
  579. </element>
  580. </start>
  581. <define name="B">
  582. <interleave>
  583. <element name="B"/>
  584. <element name="C"/>
  585. </interleave>
  586. </define>
  587. </grammar>
  588. }
  589. validator = REXML::Validation::RelaxNG.new( rng )
  590. error( validator, %q{<A><B/></A>} )
  591. error( validator, %q{<A><C/></A>} )
  592. error( validator, %q{<A><C/><C/></A>} )
  593. no_error( validator, %q{<A><B/><C/></A>} )
  594. no_error( validator, %q{<A><C/><B/></A>} )
  595. rng = %q{
  596. <?xml version="1.0" encoding="UTF-8"?>
  597. <grammar xmlns="http://relaxng.org/ns/structure/1.0">
  598. <start>
  599. <element name="A">
  600. <interleave>
  601. <ref name="B"/>
  602. <ref name="C"/>
  603. </interleave>
  604. </element>
  605. </start>
  606. <define name="B">
  607. <element name="B"/>
  608. </define>
  609. <define name="C">
  610. <element name="C"/>
  611. </define>
  612. </grammar>
  613. }
  614. validator = REXML::Validation::RelaxNG.new( rng )
  615. error( validator, %q{<A><B/></A>} )
  616. error( validator, %q{<A><C/></A>} )
  617. error( validator, %q{<A><C/><C/></A>} )
  618. no_error( validator, %q{<A><B/><C/></A>} )
  619. no_error( validator, %q{<A><C/><B/></A>} )
  620. end
  621. def test_ref_recurse
  622. rng = %q{
  623. <?xml version="1.0" encoding="UTF-8"?>
  624. <grammar xmlns="http://relaxng.org/ns/structure/1.0">
  625. <start>
  626. <element name="A">
  627. <ref name="B"/>
  628. </element>
  629. </start>
  630. <define name="B">
  631. <element name="B">
  632. <optional>
  633. <ref name="B"/>
  634. </optional>
  635. </element>
  636. </define>
  637. </grammar>
  638. }
  639. validator = REXML::Validation::RelaxNG.new( rng )
  640. error( validator, %q{<A></A>} )
  641. no_error( validator, %q{<A><B/></A>} )
  642. no_error( validator, %q{<A><B><B/></B></A>} )
  643. end
  644. def test_ref_optional
  645. rng = %q{
  646. <?xml version="1.0" encoding="UTF-8"?>
  647. <grammar xmlns="http://relaxng.org/ns/structure/1.0">
  648. <start>
  649. <element name="A">
  650. <optional>
  651. <ref name="B"/>
  652. </optional>
  653. </element>
  654. </start>
  655. <define name="B">
  656. <element name="B">
  657. </element>
  658. </define>
  659. </grammar>
  660. }
  661. validator = REXML::Validation::RelaxNG.new( rng )
  662. no_error( validator, %q{<A></A>} )
  663. no_error( validator, %q{<A><B/></A>} )
  664. error( validator, %q{<A><B/><B/></A>} )
  665. error( validator, %q{<A><C/></A>} )
  666. rng = %q{
  667. <?xml version="1.0" encoding="UTF-8"?>
  668. <grammar xmlns="http://relaxng.org/ns/structure/1.0">
  669. <start>
  670. <element name="A">
  671. <ref name="B"/>
  672. </element>
  673. </start>
  674. <define name="B">
  675. <optional>
  676. <element name="B">
  677. </element>
  678. </optional>
  679. </define>
  680. </grammar>
  681. }
  682. validator = REXML::Validation::RelaxNG.new( rng )
  683. no_error( validator, %q{<A></A>} )
  684. no_error( validator, %q{<A><B/></A>} )
  685. error( validator, %q{<A><B/><B/></A>} )
  686. error( validator, %q{<A><C/></A>} )
  687. end
  688. def error( validator, source )
  689. parser = REXML::Parsers::TreeParser.new( source )
  690. parser.add_listener( validator.reset )
  691. assert_raise( REXML::Validation::ValidationException,
  692. "Expected a validation error" ) { parser.parse }
  693. end
  694. def no_error( validator, source )
  695. parser = REXML::Parsers::TreeParser.new( source )
  696. parser.add_listener( validator.reset )
  697. assert_nothing_raised { parser.parse }
  698. end
  699. end
  700. end