Mercurial > pub > Impl
annotate Lib/IMPL/Web/View/TTLoader.pm @ 250:129e48bb5afb
DOM refactoring
ObjectToDOM methods are virtual
QueryToDOM uses inflators
Fixed transform for the complex values in the ObjectToDOM
QueryToDOM doesn't allow to use complex values (HASHes) as values for nodes (overpost problem)
author | sergey |
---|---|
date | Wed, 07 Nov 2012 04:17:53 +0400 |
parents | 5c82eec23bb6 |
children | 6b6d4b2275a1 |
rev | line source |
---|---|
181 | 1 package IMPL::Web::View::TTLoader; |
2 use strict; | |
3 | |
232 | 4 use IMPL::lang qw(:declare); |
181 | 5 |
6 use Template::Provider(); | |
7 use Template::Context(); | |
8 use Template::Constants qw(:status); | |
9 | |
10 use IMPL::Web::View::TTDocument(); | |
11 | |
12 use parent qw( | |
194 | 13 IMPL::Object |
196 | 14 IMPL::Object::Serializable |
181 | 15 ); |
16 | |
17 BEGIN { | |
194 | 18 public property options => PROP_ALL; |
19 public property provider => PROP_GET | PROP_OWNERSET; | |
20 public property context => PROP_GET | PROP_OWNERSET; | |
21 public property ext => PROP_ALL; | |
195
7a920771fd8e
IMPL::Web::View changed document layout handling, docs, examples
cin
parents:
194
diff
changeset
|
22 public property layoutBase => PROP_GET | PROP_OWNERSET; |
194 | 23 |
24 public property isInitialized => PROP_GET | PROP_OWNERSET; | |
25 public property initializer => PROP_GET | PROP_OWNERSET; | |
26 | |
27 private property _globals => PROP_ALL; | |
181 | 28 } |
29 | |
196 | 30 sub save { |
31 my ($this,$context) = @_; | |
32 | |
33 $context->AddVar($_, $this->$_()) for qw(options provider context ext layoutBase); | |
34 } | |
35 | |
36 sub restore { | |
37 my ($class,$data,$surrogate) = @_; | |
38 | |
39 my %params = @$data; | |
40 | |
41 my $refOpts = delete $params{options}; | |
42 | |
43 if ($surrogate){ | |
44 $surrogate->callCTOR($refOpts,%params); | |
45 } else { | |
46 $surrogate = $class->new($refOpts,%params); | |
47 } | |
206 | 48 return $surrogate; |
196 | 49 } |
50 | |
181 | 51 sub CTOR { |
194 | 52 my ($this,$refOpts,%args) = @_; |
53 | |
54 $refOpts ||= {}; | |
55 | |
56 $this->ext($args{ext}) if $args{ext}; | |
57 $this->initializer($args{initializer}) if $args{initializer}; | |
58 $this->_globals(ref $args{globals} eq 'HASH' ? $args{globals} : {}); | |
59 | |
60 $this->options($refOpts); | |
195
7a920771fd8e
IMPL::Web::View changed document layout handling, docs, examples
cin
parents:
194
diff
changeset
|
61 $this->layoutBase($args{layoutBase}) if $args{layoutBase}; |
194 | 62 |
63 # to aviod cyclic references we need to do a copy of $refOpts | |
64 $refOpts->{LOAD_TEMPLATES} = $this->provider(new Template::Provider( { %$refOpts } )); | |
65 | |
66 $this->context(new Template::Context($refOpts)); | |
181 | 67 } |
68 | |
69 sub document { | |
194 | 70 my ($this,$name,$vars) = @_; |
71 | |
72 my $tt = $this->template($name); | |
73 | |
74 $this->_init(); | |
75 | |
76 my $opts = { %{ $this->options } }; | |
77 | |
78 $opts->{STASH} = $this->context->stash->clone(); | |
79 $opts->{LOAD_TEMPLATES} = $this->provider; | |
80 | |
81 return new IMPL::Web::View::TTDocument( $tt, $opts, $this, $vars ); | |
181 | 82 } |
83 | |
84 sub template { | |
194 | 85 my ($this,$name) = @_; |
86 | |
87 $name =~ s/^\s+|\s+$//g; | |
88 | |
205
891c04080658
IMPL::Web::View fixed template selection, release candidate
sergey
parents:
196
diff
changeset
|
89 die new IMPL::InvalidArgumentException("A valid template name is required") unless length $name; |
194 | 90 |
91 $name = $this->_appendExt($name); | |
92 | |
93 my ($tt,$error) = $this->provider->fetch($name); | |
94 | |
95 if (defined $error and $error == STATUS_DECLINED) { | |
96 die new IMPL::KeyNotFoundException($name); | |
97 } elsif (defined $error and $error == STATUS_ERROR) { | |
98 die new IMPL::Exception("Failed to load a template", $name, $tt); | |
99 } | |
100 | |
101 return $tt; | |
181 | 102 } |
103 | |
195
7a920771fd8e
IMPL::Web::View changed document layout handling, docs, examples
cin
parents:
194
diff
changeset
|
104 sub layout { |
7a920771fd8e
IMPL::Web::View changed document layout handling, docs, examples
cin
parents:
194
diff
changeset
|
105 my ($this,$name) = @_; |
7a920771fd8e
IMPL::Web::View changed document layout handling, docs, examples
cin
parents:
194
diff
changeset
|
106 |
7a920771fd8e
IMPL::Web::View changed document layout handling, docs, examples
cin
parents:
194
diff
changeset
|
107 my $layout; |
7a920771fd8e
IMPL::Web::View changed document layout handling, docs, examples
cin
parents:
194
diff
changeset
|
108 |
7a920771fd8e
IMPL::Web::View changed document layout handling, docs, examples
cin
parents:
194
diff
changeset
|
109 if ($this->layoutBase) { |
7a920771fd8e
IMPL::Web::View changed document layout handling, docs, examples
cin
parents:
194
diff
changeset
|
110 $layout = $this->layoutBase . "/"; |
7a920771fd8e
IMPL::Web::View changed document layout handling, docs, examples
cin
parents:
194
diff
changeset
|
111 } |
7a920771fd8e
IMPL::Web::View changed document layout handling, docs, examples
cin
parents:
194
diff
changeset
|
112 |
7a920771fd8e
IMPL::Web::View changed document layout handling, docs, examples
cin
parents:
194
diff
changeset
|
113 $layout .= $name; |
7a920771fd8e
IMPL::Web::View changed document layout handling, docs, examples
cin
parents:
194
diff
changeset
|
114 return $this->template($layout); |
7a920771fd8e
IMPL::Web::View changed document layout handling, docs, examples
cin
parents:
194
diff
changeset
|
115 } |
7a920771fd8e
IMPL::Web::View changed document layout handling, docs, examples
cin
parents:
194
diff
changeset
|
116 |
181 | 117 sub _appendExt { |
194 | 118 my ($this,$name) = @_; |
119 | |
120 return $name unless $this->ext; | |
121 | |
122 if (length $this->ext and substr( $name, -length($this->ext) ) eq $this->ext) { | |
123 return $name; | |
124 } else { | |
125 return $name . $this->ext; | |
126 } | |
181 | 127 } |
128 | |
129 sub _init { | |
194 | 130 my ($this) = @_; |
131 | |
132 if (!$this->isInitialized) { | |
133 my $initializer = $this->initializer || sub {}; | |
134 | |
135 eval { | |
136 $this->context->process($initializer,$this->_globals); | |
137 }; | |
138 if (my $e = $@) { | |
139 die new IMPL::Exception("Failed to process an initializer", $this->initializer, $e); | |
140 } | |
141 | |
142 $this->isInitialized(1); | |
143 } | |
181 | 144 } |
145 | |
146 1; | |
147 | |
148 __END__ | |
149 | |
150 =pod | |
151 | |
152 =head1 NAME | |
153 | |
154 C<IMPL::Web::View::TTLoader> - предоставляет глобальный контекст для загрузки шаблонов | |
155 | |
156 =head1 SYNOPSIS | |
157 | |
158 =begin code | |
159 | |
160 use IMPL::Web::View::TTLoader(); | |
161 | |
162 my $loader = new IMPL::Web::View::TTLoader( | |
194 | 163 { |
164 INCLUDE_PATH => [ | |
165 '/my/app/tt', | |
166 '/my/app/tt/lib' | |
167 ] | |
168 }, | |
169 ext => '.tt', | |
170 initializer => 'shared/global' | |
171 | |
181 | 172 ); |
173 | |
174 my $doc = $loader->document('index'); | |
175 | |
176 my $html = $doc->Render(); | |
177 | |
178 =end code | |
179 | |
180 =head1 DESCRIPTION | |
181 | |
182 | 182 =head1 MEMBERS |
183 | |
184 =head2 C<document($docName)> | |
185 | |
181 | 186 =cut |
187 |