Thread: [htmltmpl] html template loops (hash of a hash)
Brought to you by:
samtregar
From: Covert, J. \(JSC.\) <jco...@fo...> - 2006-08-30 17:28:46
Attachments:
smime.p7s
|
I'm a bit new to html templates, so I apologize in advance if I ask some obvious questions. I'm working on an HTML::Template loop issue that I can't quite seem to get working just right. Instead of an array of hashes, I'm using a hash of hashes. When I try and run it, it gives me this error: ----------------------- Not an ARRAY reference at ./index2.cgi line 85. ----------------------- Don't think this is a Perl error, so I'm thinking it's an HTML::Template error, maybe. Here's an example of the data set I'm using: The Perl I'm using to pack the hash of hash into something I thing HTML template will understand is below. If anyone can think of what would cause this, let me know. I think I may be trying to push the limits of HTML::Template farther than it supposed to. ---------------- Jake Covert (313) 322-6717 (desk) (313) 845-4154 (fax) ---------------- perl index2.cgi ===================================================== 80 my @loop; # the loop data will be put in here 81 82 # fill in the loop, sorted by fruit name 83 foreach my $vendor (sort keys %vendor_hoh) { 84 # get the files from the data hash 85 my ($rif, $rif_out, $graph, $raw, $percent1, $percent2, $percent3) = @{$vendor_hoh{$vendor}}; 86 87 # make a new row for this vendor - the keys are <TMPL_VAR> names 88 # and the values are the values to fill in the template. 89 my %row = ( 90 rif => $rif, 91 rif_out => $rif_out, 92 graph => $graph, 93 raw => $raw, 94 percent1 => $percent1, 95 percent2 => $percent2, 96 percent3 => $percent3 97 ); 98 99 # put this row into the loop by reference 100 push(@loop, \%row); 101 102 } 103 104 # call param to fill in the loop with the loop data by reference. 105 $tmpl->param(TMPL_LOOP => \@loop); 106 #===================================================== 107 #print @{$vendor_hoh{amls}}; 108 109 # my @loop_data; 110 # push(@loop_data, \%vendor_hoh); 111 # 112 # # Pass the listref to param() 113 # $tmpl -> param( TMPL_LOOP => \@loop_data ); 114 # 115 # 116 # This is HTML::Template part that actually outputs things... 117 # 118 print "Content-type: text/html\n\n", 119 $tmpl->output; 120 print Dumper(%vendor_hoh); ===================================================== Template(s) ====================================== I have two templates. The first is called index.tmpl.template. It's a template for the real template. I couldn't figure out how to replace the top layer of hashes, so I'm using the perl script to auto-create the real index.tmpl from index.tmpl.template based on the first layer. Perl that does this is here: ======================================= if ( /TMPL_LOOP_PLACE_HOLDER/ ) { foreach $rif_file (sort @files) { my @rif_fields = split(/\./,$rif_file); $APP = (@rif_fields)[0]; $MONTH = (@rif_fields)[1]; $vendor_hoh{$APP}->{'rif'} = "${APP}.${MONTH}.rif"; $vendor_hoh{$APP}->{'rif_out'} = "${APP}.${MONTH}.rif.out"; $vendor_hoh{$APP}->{'graph'} = "${APP}.${MONTH}.graph_toc.htm"; $vendor_hoh{$APP}->{'raw'} = "${APP}.${MONTH}.raw.gz"; $vendor_hoh{$APP}->{'percent1'} = "${APP}.${MONTH}.country_percentages.txt"; $vendor_hoh{$APP}->{'percent2'} = "${APP}Software_Usage${MONTH}.txt"; $vendor_hoh{$APP}->{'percent3'} = "${APP}Software_percent_Usage${MONTH}.txt"; print OF "\n<TMPL_LOOP NAME=\"$APP\">\n"; print OF "<TMPL_IF NAME=\"rif\"><TMPL_VAR rif></TMPL_IF>\n"; print OF "<TMPL_IF NAME=\"raw\"><TMPL_VAR raw></TMPL_IF>\n"; print OF "</TMPL_LOOP>\n\n"; } } ======================================= Example of what the template "template" looks like: =-=-=-=-=-=-=-=-=-=-=-= <TMPL_LOOP NAME="TMPL_LOOP"> <!- TMPL_LOOP_PLACE_HOLDER -> </TMPL_LOOP> =-=-=-=-=-=-=-=-=-=-=-= When my index.cgi script runs, it reads this index.tmpl.template and replaces <!- TMPL_LOOP_PLACE_HOLDER -> with the real data of: <TMPL_LOOP NAME="$APP"> <TMPL_IF NAME="rif"><TMPL_VAR rif></TMPL_IF> <TMPL_IF NAME="raw"><TMPL_VAR raw></TMPL_IF> </TMPL_LOOP> Where $APP is the main key of my hash of hash. Example of the finished index.tmpl is below: =-=-=-=-=-=-=-=-=-=-=-= <TMPL_LOOP NAME="TMPL_LOOP"> <TMPL_LOOP NAME="application_1"> <TMPL_IF NAME="rif"><TMPL_VAR rif></TMPL_IF> <TMPL_IF NAME="raw"><TMPL_VAR raw></TMPL_IF> </TMPL_LOOP> <TMPL_LOOP NAME="application_2"> <TMPL_IF NAME="rif"><TMPL_VAR rif></TMPL_IF> <TMPL_IF NAME="raw"><TMPL_VAR raw></TMPL_IF> </TMPL_LOOP> <TMPL_LOOP NAME="application_3"> <TMPL_IF NAME="rif"><TMPL_VAR rif></TMPL_IF> <TMPL_IF NAME="raw"><TMPL_VAR raw></TMPL_IF> </TMPL_LOOP> <TMPL_LOOP NAME="application_4"> <TMPL_IF NAME="rif"><TMPL_VAR rif></TMPL_IF> <TMPL_IF NAME="raw"><TMPL_VAR raw></TMPL_IF> </TMPL_LOOP> <!- TMPL_LOOP_PLACE_HOLDER -> </TMPL_LOOP> =-=-=-=-=-=-=-=-=-=-=-= |
From: Di D. M. <mdi...@si...> - 2006-08-30 18:03:26
|
I'm no expert, but I believe it's because you didn't pack the hash with an array. For instance; $tmplvar->{hashkey} =3D "aa" is wrong $tmplvar->[0]->{hashkey} =3D "aa" is right So for a hash of hashes your string would be $tmplvar->[0]->{hashkey}->[0]->{hashkey} =3D "aa" -----Original Message----- From: htm...@li... [mailto:htm...@li...] On Behalf Of Covert, Jake (JSC.) Sent: Wednesday, August 30, 2006 1:27 PM To: htm...@li... Subject: [htmltmpl] html template loops (hash of a hash) I'm a bit new to html templates, so I apologize in advance if I ask some obvious questions. I'm working on an HTML::Template loop issue that I can't quite seem to get=20 working just right. Instead of an array of hashes, I'm using a hash of=20 hashes. When I try and run it, it gives me this error: ----------------------- Not an ARRAY reference at ./index2.cgi line 85. ----------------------- Don't think this is a Perl error, so I'm thinking it's an HTML::Template error, maybe. Here's an example of the data set I'm using: The Perl I'm using to pack the hash of hash into something I thing HTML=20 template will understand is below. If anyone can think of what would cause this, let me know. I think I may be=20 trying to push the limits of HTML::Template farther than it supposed to. ----------------=20 Jake Covert (313) 322-6717 (desk) (313) 845-4154 (fax) ---------------- perl index2.cgi =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D 80 my @loop; # the loop data will be put in here 81 82 # fill in the loop, sorted by fruit name 83 foreach my $vendor (sort keys %vendor_hoh) { 84 # get the files from the data hash 85 my ($rif, $rif_out, $graph, $raw, $percent1, $percent2, $percent3)=20 =3D @{$vendor_hoh{$vendor}}; 86 87 # make a new row for this vendor - the keys are <TMPL_VAR> names 88 # and the values are the values to fill in the template. 89 my %row =3D ( 90 rif =3D> $rif, 91 rif_out =3D> $rif_out, 92 graph =3D> $graph, 93 raw =3D> $raw, 94 percent1 =3D> $percent1, 95 percent2 =3D> $percent2, 96 percent3 =3D> $percent3 97 ); 98 99 # put this row into the loop by reference 100 push(@loop, \%row); 101 102 } 103 104 # call param to fill in the loop with the loop data by reference. 105 $tmpl->param(TMPL_LOOP =3D> \@loop); 106 = #=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D 107 #print @{$vendor_hoh{amls}}; 108 109 # my @loop_data; 110 # push(@loop_data, \%vendor_hoh); 111 # 112 # # Pass the listref to param() 113 # $tmpl -> param( TMPL_LOOP =3D> \@loop_data ); 114 # 115 # 116 # This is HTML::Template part that actually outputs things... 117 # 118 print "Content-type: text/html\n\n", 119 $tmpl->output; 120 print Dumper(%vendor_hoh); =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D Template(s) =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D I have two templates. The first is called index.tmpl.template. It's a template for the real template. I couldn't figure out how to replace the top=20 layer of hashes, so I'm using the perl script to auto-create the real=20 index.tmpl from index.tmpl.template based on the first layer. Perl that does=20 this is here: =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D if ( /TMPL_LOOP_PLACE_HOLDER/ ) { foreach $rif_file (sort @files) { my @rif_fields =3D split(/\./,$rif_file); $APP =3D (@rif_fields)[0]; $MONTH =3D (@rif_fields)[1]; $vendor_hoh{$APP}->{'rif'} =3D "${APP}.${MONTH}.rif"; $vendor_hoh{$APP}->{'rif_out'} =3D "${APP}.${MONTH}.rif.out"; $vendor_hoh{$APP}->{'graph'} =3D "${APP}.${MONTH}.graph_toc.htm"; $vendor_hoh{$APP}->{'raw'} =3D "${APP}.${MONTH}.raw.gz"; $vendor_hoh{$APP}->{'percent1'} =3D=20 "${APP}.${MONTH}.country_percentages.txt"; $vendor_hoh{$APP}->{'percent2'} =3D "${APP}Software_Usage${MONTH}.txt"; $vendor_hoh{$APP}->{'percent3'} =3D=20 "${APP}Software_percent_Usage${MONTH}.txt"; print OF "\n<TMPL_LOOP NAME=3D\"$APP\">\n"; print OF "<TMPL_IF NAME=3D\"rif\"><TMPL_VAR = rif></TMPL_IF>\n"; print OF "<TMPL_IF NAME=3D\"raw\"><TMPL_VAR = raw></TMPL_IF>\n"; print OF "</TMPL_LOOP>\n\n"; } } =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D Example of what the template "template" looks like: =3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D <TMPL_LOOP NAME=3D"TMPL_LOOP"> <!- TMPL_LOOP_PLACE_HOLDER -> </TMPL_LOOP> =3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D When my index.cgi script runs, it reads this index.tmpl.template and replaces <!- TMPL_LOOP_PLACE_HOLDER -> with the real data of: <TMPL_LOOP NAME=3D"$APP"> <TMPL_IF NAME=3D"rif"><TMPL_VAR rif></TMPL_IF> <TMPL_IF NAME=3D"raw"><TMPL_VAR raw></TMPL_IF> </TMPL_LOOP> Where $APP is the main key of my hash of hash. Example of the finished index.tmpl is below: =3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D <TMPL_LOOP NAME=3D"TMPL_LOOP"> <TMPL_LOOP NAME=3D"application_1"> <TMPL_IF NAME=3D"rif"><TMPL_VAR rif></TMPL_IF> <TMPL_IF NAME=3D"raw"><TMPL_VAR raw></TMPL_IF> </TMPL_LOOP> <TMPL_LOOP NAME=3D"application_2"> <TMPL_IF NAME=3D"rif"><TMPL_VAR rif></TMPL_IF> <TMPL_IF NAME=3D"raw"><TMPL_VAR raw></TMPL_IF> </TMPL_LOOP> <TMPL_LOOP NAME=3D"application_3"> <TMPL_IF NAME=3D"rif"><TMPL_VAR rif></TMPL_IF> <TMPL_IF NAME=3D"raw"><TMPL_VAR raw></TMPL_IF> </TMPL_LOOP> <TMPL_LOOP NAME=3D"application_4"> <TMPL_IF NAME=3D"rif"><TMPL_VAR rif></TMPL_IF> <TMPL_IF NAME=3D"raw"><TMPL_VAR raw></TMPL_IF> </TMPL_LOOP> <!- TMPL_LOOP_PLACE_HOLDER -> </TMPL_LOOP> =3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D |
From: Karen <kar...@gm...> - 2006-08-30 20:11:55
|
On 8/30/06, Covert, Jake (JSC.) <jco...@fo...> wrote: > Don't think this is a Perl error, so I'm thinking it's an HTML::Template > error, maybe. Yep, it's actually a Perl error. It's complaining about "@{$vendor_hoh{$vendor}}" in line 85: > 85 my ($rif, $rif_out, $graph, $raw, $percent1, $percent2, $percent3) > = @{$vendor_hoh{$vendor}}; Whatever's in $vender_hoh{$vendor}, it's not an arrayref. The problem is earlier in your code. Once %vendor_hoh is populated correctly, your code should work fine, though you could shorten it thus (assuming I haven't made any brainos): $tmpl->param( TMPL_LOOP, [ map { rif => $vendor_hoh{$_}->[0], rif_out => $vendor_hoh{$_}->[1], graph => $vendor_hoh{$_}->[2], raw => $vendor_hoh{$_}->[3], percent1 => $vendor_hoh{$_}->[4], percent2 => $vendor_hoh{$_}->[5], percent3 => $vendor_hoh{$_}->[6], }, sort keys %vender_hoh ] ); |