[Catalyst] List/Scalar Context with TT + DBIC

Andreas Marienborg omega at palle.net
Thu Jun 1 14:50:06 CEST 2006


On 1. jun. 2006, at 14.43, Christopher H. Laco wrote:

> Mark Blythe wrote:
>> Thanks for the suggestion, but unfortunately it didn't work.  The
>> behavior didn't change at all with the added "cache => 1" attribute.
>> Here's the simple test template:
>>
>> [% SET results = c.model('DB::Foo').search({ col => $value },  
>> { cache =>
>> 1 }) %]
>>
>> [% results %]
>>
>> This yields:
>>
>> ARRAY(0x355f004)
>>
>> Indeed, it's an array that I can then loop through and access the
>> rows.  I guess I'll have to write some non-template perl code
>> somewhere to solve this -- or wait for the search_rs method that
>> phaylon mentioned.
>>
>
> Just to illustrate this problem in another way, here's one of the  
> Handel
> TT plugins:
>
> http://handelframework.com/source/branches/DBIC-1.0/lib/Template/ 
> Plugin/Handel/Cart.pm
>
> Specifically, this method:
>
>> sub items {
>>     my ($self, $filter) = @_;
>>     my $iterator = $self->SUPER::items($filter);
>>     my $count = $iterator->count;
>>
>>     return $iterator;
>> };
>
> If I comment out the my $count line, TT turns what it sees into an
> ARRAYREF. With the count line in, it gets the iterator as expected.
>
> In fact, even something like warn $iterator triggers TT to do the  
> right
> thing.
>
> I don't think this is DBICs problem really, but I'm more curious as to
> what is really going in in this situation.


Its the lazyness of DBIC. When you do ->count, the $iterator has to  
go to the DB, thus performing the query, and $iterator is indeed an  
$iterator. If you do not do the ->count, the $iterator is just an  
ready-to-go dbic object, that hasnt yet done anything with the DB,  
and as a result, when TT calles iterator, it gets called in list- 
context (which I believe TT always does), and the result is an array.

any clearer?


andreas





More information about the Catalyst mailing list