Mercurial > pub > Impl
annotate Lib/IMPL/Web/QueryHandler/PageFormat.pm @ 221:e997e6fbac0b
sync: working on resources schema
| author | sergey | 
|---|---|
| date | Fri, 24 Aug 2012 16:24:14 +0400 | 
| parents | 4d0e1962161c | 
| children | 
| rev | line source | 
|---|---|
| 62 | 1 package IMPL::Web::QueryHandler::PageFormat; | 
| 166 | 2 use parent qw(IMPL::Web::QueryHandler IMPL::Object::Autofill); | 
| 136 | 3 use strict; | 
| 62 | 4 | 
| 5 __PACKAGE__->PassThroughArgs; | |
| 6 | |
| 140 
fb896377389f
to_json and escape_string functions for the templates
 wizard parents: 
137diff
changeset | 7 use JSON; | 
| 62 | 8 use IMPL::Class::Property; | 
| 77 | 9 use IMPL::Web::TT::Document; | 
| 136 | 10 use Template::Plugin::URL; | 
| 171 | 11 use IMPL::Security::Context(); | 
| 12 use File::Spec(); | |
| 13 use HTML::TreeBuilder(); | |
| 14 use URI(); | |
| 63 
76b878ad6596
Added serialization support for the IMPL::Object::List
 wizard parents: 
62diff
changeset | 15 use Error qw(:try); | 
| 171 | 16 use Encode(); | 
| 62 | 17 | 
| 136 | 18 $Template::Plugin::URL::JOINT = '&'; | 
| 19 | |
| 64 | 20 BEGIN { | 
| 194 | 21 public property templatesCharset => prop_all; | 
| 22 public property templatesBase => prop_all; | |
| 23 public property includes => prop_all | prop_list; | |
| 24 public property pathinfoPrefix => prop_all; | |
| 25 public property cache => prop_all; | |
| 26 public property preprocess => prop_all; | |
| 27 public property formatOutput => prop_all; | |
| 28 public property template => prop_all; | |
| 64 | 29 } | 
| 30 | |
| 31 sub CTOR { | |
| 194 | 32 my ($this) = @_; | 
| 33 | |
| 34 $this->templatesCharset('utf-8') unless $this->templatesCharset; | |
| 35 $this->cache(File::Spec->rel2abs($this->cache)) if $this->cache; | |
| 36 $this->templatesBase(File::Spec->rel2abs($this->templatesBase)) if $this->templatesBase; | |
| 64 | 37 } | 
| 38 | |
| 62 | 39 sub Process { | 
| 194 | 40 my ($this,$action,$nextHandler) = @_; | 
| 41 | |
| 42 my $doc = new IMPL::Web::TT::Document(cache => $this->cache, preprocess => $this->preprocess); | |
| 43 | |
| 44 try { | |
| 97 | 45 | 
| 194 | 46 $this->templatesBase($ENV{DOCUMENT_ROOT}) unless $this->templatesBase; | 
| 47 | |
| 48 my ($requestUri) = split( /\?/, $ENV{REQUEST_URI} ); | |
| 49 | |
| 50 my $pathInfo; | |
| 51 my @root = (''); | |
| 52 my @base; | |
| 53 | |
| 54 if ( $requestUri eq $ENV{SCRIPT_NAME}.$ENV{PATH_INFO} ) { | |
| 55 # CGI with path info, for example | |
| 56 # /base/cgi-bin/myscript.cgi/path/info | |
| 57 # PATH_INFO will be /path/info | |
| 58 $pathInfo = $ENV{PATH_INFO}; | |
| 59 } else { | |
| 60 # usual url, for exmaple | |
| 61 # /base/script.cgi will have PATH_INFO /base/script.cgi | |
| 62 # /base/ will have PATH_INFO /base/index.cgi (if index.cgi is a DirectoryIndex) | |
| 63 $pathInfo = $ENV{PATH_INFO}; | |
| 64 | |
| 65 if (my $rx = $this->pathinfoPrefix) { | |
| 66 $requestUri =~ s/^($rx)//; | |
| 67 $pathInfo =~ s/^($rx)//; | |
| 68 push @root, grep $_, split /\//, $1 if $1; | |
| 69 } | |
| 70 } | |
| 71 | |
| 72 @base = grep $_, split /\//, ($pathInfo ? substr $requestUri,0, -length($pathInfo) : $requestUri); | |
| 73 | |
| 74 local $ENV{PATH_INFO} = $pathInfo; | |
| 75 | |
| 76 my @path = grep $_, split /\//, ($ENV{PATH_INFO} || '') or die new IMPL::Exception("PATH_INFO is empty and no defaultTarget specified" ); | |
| 77 | |
| 78 my @pathContainer = @path; | |
| 79 pop @pathContainer; | |
| 80 | |
| 81 $doc->LoadFile ( | |
| 82 ($this->template || File::Spec->catfile($this->templatesBase,@path)), | |
| 83 $this->templatesCharset, | |
| 84 [$this->templatesBase, $this->includes], | |
| 85 { | |
| 86 result => scalar($nextHandler->()), | |
| 87 action => $action, | |
| 88 app => $action->application, | |
| 89 | |
| 90 absoluteUrl => sub { new URI(join ('/', @root, $_[0]) ) }, | |
| 91 baseUrl => sub { new URI (join ('/', @root, @base, $_[0]) ) }, | |
| 92 relativeUrl => sub { new URI(join ('/', @root, @base, @pathContainer,$_[0]) ) }, | |
| 93 | |
| 94 user => IMPL::Security::Context->current->principal, | |
| 95 session => IMPL::Security::Context->current, | |
| 96 | |
| 97 to_json => \&to_json, | |
| 98 escape_string => sub { $_[0] =~ s/"/"/g; $_[0] }, | |
| 99 } | |
| 100 ); | |
| 101 | |
| 102 $action->response->contentType('text/html'); | |
| 103 my $hOut = $action->response->streamBody; | |
| 104 if ($this->formatOutput == 1) { | |
| 105 my $tree = new HTML::TreeBuilder(); | |
| 106 try { | |
| 107 $tree->parse_content($doc->Render()); | |
| 108 print $hOut $tree->as_HTML('<>&'," ",{}); | |
| 109 } finally { | |
| 110 $tree->delete; | |
| 111 }; | |
| 112 } elsif ($this->formatOutput() == 2 ) { | |
| 113 (my $data = $doc->Render()) =~ s/\s+/ /g; | |
| 114 print $hOut $data; | |
| 115 } else { | |
| 116 print $hOut $doc->Render(); | |
| 117 } | |
| 118 } finally { | |
| 119 $doc->Dispose; | |
| 120 }; | |
| 62 | 121 } | 
| 122 | |
| 154 | 123 sub URI::_query::new_params { | 
| 194 | 124 my ($this,$params) = @_; | 
| 125 | |
| 126 my $clone = $this->clone; | |
| 127 if (ref $params eq 'HASH' ) { | |
| 128 my %newParams = ($clone->query_form , %$params); | |
| 129 $clone->query_form(map { $_, ( Encode::is_utf8( $newParams{$_} ) ? Encode::encode('utf-8', $newParams{$_}) : $newParams{$_} ) } sort keys %newParams ); | |
| 130 } | |
| 131 return $clone; | |
| 154 | 132 } | 
| 133 | |
| 65 | 134 1; | 
| 135 | |
| 136 __END__ | |
| 137 | |
| 138 =pod | |
| 139 | |
| 140 =head1 NAME | |
| 141 | |
| 180 | 142 C<IMPL::Web::QueryHandler::PageFormat> - Выдача результатов в виде HTML страницы, построенной из шаблона. | 
| 65 | 143 | 
| 144 =head1 SYNOPSIS | |
| 145 | |
| 180 | 146 В файле конфигурации приложения | 
| 65 | 147 | 
| 148 =begin code xml | |
| 149 | |
| 150 <handlersQuery type="IMPL::Object::List"> | |
| 194 | 151 <item type="IMPL::Web::QueryHandler::PageFormat"> | 
| 152 <charsetTemplates>utf-8</charsetTemplates> | |
| 153 </item> | |
| 65 | 154 </handlersQuery> | 
| 155 | |
| 156 =end code xml | |
| 157 | |
| 180 | 158 Программно | 
| 65 | 159 | 
| 160 =begin code | |
| 161 | |
| 162 my $app = new IMPL::Web::Application(); | |
| 163 $app->handlersQuery->Add( | |
| 194 | 164 new IMPL::Web::QueryHandler::PageFormat( charsetTemplates=> 'utf-8' ); | 
| 65 | 165 ); | 
| 166 | |
| 167 =end | |
| 168 | |
| 169 =head1 DESCRIPTION | |
| 170 | |
| 180 | 171 Обработчик запроса для веб приложения. Загружает шаблон, путь к котрому берется | 
| 172 из C<ENV{PATH_INFO}> относительно пути из свойства C<templatesBase>. | |
| 65 | 173 | 
| 180 | 174 Наследуется от C<IMPL::Web::QueryHandler> для реализации функционала | 
| 175 обработчика запроса и переопределяет метод C<Process>. | |
| 65 | 176 | 
| 177 C<Serializable> | |
| 178 | |
| 179 =head1 MEMBERS | |
| 180 | |
| 181 =over | |
| 182 | |
| 183 =item C<CTOR(%props)> | |
| 184 | |
| 180 | 185 Создает новый экземпляр и заполняет свойства. | 
| 65 | 186 | 
| 187 =item C<[get,set] templatesCharset> | |
| 188 | |
| 180 | 189 Кодировка шаблонов. По умолчанию utf-8. | 
| 65 | 190 | 
| 191 =item C<[get,set] templatesBase> | |
| 192 | |
| 180 | 193 Каталог относительно которого ищется шаблон. | 
| 65 | 194 | 
| 195 =item C<[override] Process($action,$nextHandler)> | |
| 196 | |
| 180 | 197 Метод, переопределяющий C<IMPL::Web::QueryHandler->Process> и которому передается управление | 
| 198 для выполнения действий. | |
| 65 | 199 | 
| 200 =back | |
| 201 | |
| 180 | 202 =cut | 
