Using Traits to Maintain State

by Curtis Poe

Some of you might recall chromatic's review of Class::Trait, a module which implements traits (PDF) in Perl. He gave a couple of good examples of how one can use traits and I figured a follow-up on one of my many "real world" uses of traits and how it has simplified my code.


2006-10-24 06:44:00
There is a typo in the final line of code which reads:

Becomes this:

@serves = grep { $_->is_selected } @servers

Unless I'm mistaken the "@serves" should be "@servers".

Matt S Trout
2007-05-09 12:56:59
I would've thought you could just load Class::InsideOut and use register/id/private to store your data. It should handle all the cleanup etc. for you.
2007-05-10 00:59:42

Matt: I've also had Object::InsideOut suggested, but when I've tested it, this cleanup does not happen. The calling code does not change, but my trait now looks like this:

package Trait::Selected;

use strict;
use warnings;

use Class::InsideOut qw( id private register );
use Class::Trait 'base';
our @REQUIRES = qw(id);

private selected => my %is_selected;

sub is_selected {
my $self = shift;
my $id = id $self;
unless ( exists $is_selected{$id} ) {
register(ref $self);
$is_selected{$id} ||= 0;
return $is_selected{$id} unless @_;
$is_selected{$id} = shift;
return $self;

use Data::Dumper;
END { print Dumper \%is_selected }

That Dumper call in the END block shows that the id is still hanging around and that's the problem I need to solve.