Mercurial > pub > Impl
comparison Lib/IMPL/DOM/Schema/NodeList.pm @ 8:fffb153be599
DOM Schema
author | Sergey |
---|---|
date | Tue, 25 Aug 2009 17:36:37 +0400 |
parents | |
children | 1ca530e5c9c5 |
comparison
equal
deleted
inserted
replaced
7:94d47b388442 | 8:fffb153be599 |
---|---|
1 package IMPL::DOM::Schema::NodeList; | |
2 use strict; | |
3 use warnings; | |
4 use base qw(IMPL::DOM::Schema::Item); | |
5 use IMPL::Class::Property; | |
6 | |
7 BEGIN { | |
8 public property MessageUnexpected => prop_all; | |
9 public property MessageNodesRequired => prop_all; | |
10 } | |
11 | |
12 sub Validate { | |
13 my ($this,$node) = @_; | |
14 | |
15 my @nodes = map { | |
16 {nodeName => $_->nodeName, Schema => $_, Min => $_->minOccur, Max => $_->maxOccur, Seen => 0 } | |
17 } @{$this->childNodes}; | |
18 | |
19 my $info = shift @nodes; | |
20 | |
21 foreach my $child ( @{$node->childNodes} ) { | |
22 #skip schema elements | |
23 while ($info and $info->{nodeName} ne $child->nodeName) { | |
24 # if possible of course :) | |
25 return { | |
26 Error => 1, | |
27 Message => $this->MessageUnexpected, | |
28 Node => $child, | |
29 Source => $this | |
30 } if $info->{Min} > $info->{Seen}; | |
31 | |
32 $info = shift @nodes; | |
33 } | |
34 | |
35 # return error if no more children allowed | |
36 return { | |
37 Error => 1, | |
38 Message => $this->MessageUnexpected, | |
39 Node => $child, | |
40 Source => $this | |
41 } unless $info; | |
42 | |
43 # it's ok, we found schema element for him | |
44 $info->{Seen}++; | |
45 | |
46 # check count limits | |
47 return { | |
48 Error => 1, | |
49 Message => $this->MessageUnexpected, | |
50 Node => $child, | |
51 Source => $this, | |
52 } if $info->{Seen} > $info->{Max}; | |
53 | |
54 # validate | |
55 if (my @errors = $info->{Schema}->Validate($child)) { | |
56 return @errors; | |
57 } | |
58 } | |
59 | |
60 # no more children left (but may be should :) | |
61 while ($info) { | |
62 return { | |
63 Error => 1, | |
64 Message => $this->MessageNodesRequired, | |
65 Source => $this | |
66 } if $info->{Seen} < $info->{Min}; | |
67 | |
68 $info = shift @nodes; | |
69 } | |
70 } | |
71 | |
72 1; | |
73 | |
74 __END__ | |
75 | |
76 =pod | |
77 | |
78 =head1 DESCRIPTION | |
79 | |
80 Содержимое для сложного узла. Порядок важен. Дочерними элементами могут быть | |
81 только C<IMPL::DOM::Schema::ComplexNode> и C<IMPL::DOM::Schema::SimpleNode>. | |
82 | |
83 =cut |