Mercurial > pub > Impl
annotate Lib/IMPL/DOM/XMLReader.pm @ 111:6c25ea91c985
ControllerUnit concept
| author | wizard |
|---|---|
| date | Tue, 18 May 2010 01:33:37 +0400 |
| parents | 196bf443b5e1 |
| children | 7b14e0122b79 |
| rev | line source |
|---|---|
| 49 | 1 package IMPL::DOM::XMLReader; |
| 2 use strict; | |
| 3 use warnings; | |
| 4 | |
| 5 use base qw(IMPL::Object IMPL::Object::Autofill); | |
| 6 use IMPL::Class::Property; | |
| 7 use IMPL::Class::Property::Direct; | |
| 8 use XML::Parser; | |
|
104
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
9 require IMPL::DOM::Schema; |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
10 require IMPL::DOM::Navigator::Builder; |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
11 require IMPL::DOM::Navigator::SimpleBuilder; |
| 49 | 12 |
| 13 __PACKAGE__->PassThroughArgs; | |
| 14 | |
| 15 BEGIN { | |
| 16 public _direct property Navigator => prop_get | owner_set; | |
| 17 private _direct property _current => prop_all; | |
| 18 private _direct property _text => prop_all; | |
| 19 private _direct property _textHistory => prop_all; | |
| 20 } | |
| 21 | |
| 22 sub Parse { | |
| 23 my ($this,$in) = @_; | |
| 24 | |
| 25 my $parser = new XML::Parser( | |
| 26 Handlers => { | |
| 27 Start => sub {shift; goto &OnStart($this,@_)}, | |
| 28 End => sub {shift; goto &OnEnd($this,@_)}, | |
| 29 Char => sub {shift; goto &OnChar($this,@_)} | |
| 30 } | |
| 31 ); | |
| 32 | |
| 33 $parser->parse($in); | |
| 34 } | |
| 35 | |
| 36 sub ParseFile { | |
| 37 my ($this,$in) = @_; | |
| 38 | |
| 39 my $parser = new XML::Parser( | |
| 40 Handlers => { | |
| 41 Start => sub {shift; unshift @_, $this; goto &_OnBegin;}, | |
| 42 End => sub {shift; unshift @_, $this; goto &_OnEnd;}, | |
| 43 Char => sub {shift; unshift @_, $this; goto &_OnChar;} | |
| 44 } | |
| 45 ); | |
| 46 | |
| 47 $parser->parsefile($in); | |
| 48 } | |
| 49 | |
| 50 sub _OnBegin { | |
| 51 my ($this,$element,%attrs) = @_; | |
| 52 | |
| 53 push @{$this->{$_textHistory}},$this->{$_text}; | |
| 54 $this->{$_text} = ""; | |
| 55 $this->{$_current} = $this->Navigator->NavigateCreate($element,%attrs); | |
| 56 } | |
| 57 | |
| 58 sub _OnEnd { | |
| 59 my ($this,$element) = @_; | |
|
104
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
60 $this->{$_current}->nodeValue($this->Navigator->inflateValue( $this->{$_text}, $this->{$_current} ) ) if length $this->{$_text}; |
| 49 | 61 $this->{$_text} = pop @{$this->{$_textHistory}}; |
| 62 $this->{$_current} = $this->Navigator->Back; | |
| 63 } | |
| 64 | |
| 65 sub _OnChar { | |
| 66 my ($this,$val) = @_; | |
| 67 $this->{$_text} .= $val; | |
| 68 } | |
| 69 | |
|
104
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
70 sub LoadDocument { |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
71 my ($self,$file,$schema) = @_; |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
72 |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
73 my $parser; |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
74 if ($schema) { |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
75 $schema = IMPL::DOM::Schema->LoadSchema($schema) if not ref $schema; |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
76 $parser = $self->new( |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
77 Navigator => IMPL::DOM::Navigator::Builder->new( |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
78 'IMPL::DOM::Document', |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
79 $schema |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
80 ) |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
81 ); |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
82 } else { |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
83 $parser = $self->new( |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
84 Navigator => IMPL::DOM::Navigator::SimpleBuilder->new() |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
85 ); |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
86 } |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
87 |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
88 $parser->ParseFile($file); |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
89 my $doc = $parser->Navigator->Document; |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
90 if ($schema) { |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
91 my @errors = $parser->Navigator->BuildErrors; |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
92 push @errors, $schema->Validate($doc); |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
93 die new IMPL::Exception("Loaded document doesn't match the schema", @errors) if @errors; |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
94 } |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
95 return $doc; |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
96 } |
|
196bf443b5e1
DOM::Schema RC0 inflators support, validation and some other things,
wizard
parents:
103
diff
changeset
|
97 |
| 49 | 98 1; |
| 99 | |
| 100 __END__ | |
| 101 | |
| 102 =pod | |
| 103 | |
| 104 =head1 SYNOPSIS | |
| 105 | |
| 106 my $reader = new IMPL::DOM::XMLReader(Navigator => $DomBuilder); | |
| 107 my $obj = $reader->parsefile("data.xml"); | |
| 108 | |
| 109 =head1 DESCRIPTION | |
| 110 | |
| 111 Простой класс, использующий навигатор для постороения документа. В зависимости от | |
| 112 используемого навигатора может быть получен различный результат. | |
| 113 | |
| 114 Навигатор должен поодерживать методы C<NavigateCreate> и C<Back> | |
| 115 | |
| 116 =head1 METHODS | |
| 117 | |
| 118 =over | |
| 119 | |
| 120 =item C<CTOR(Naviagtor => $builder)> | |
| 121 | |
| 122 Создает новый экземпляр парсера, с указанным навигатором для построения документа | |
| 123 | |
| 124 =item C<$obj->Parse($in)> | |
| 125 | |
| 126 Строит документ. На вход получает либо xml строку, либо HANDLE. | |
| 127 | |
| 128 =item C<$obj->ParseFile($fileName)> | |
| 129 | |
| 130 Строит документ из файла с именем C<$fileName>. | |
| 131 | |
| 132 =back | |
| 133 | |
| 134 =cut |
