Elastic-Model

 view release on metacpan or  search on metacpan

lib/Elastic/Manual/Scoping.pod  view on Meta::CPAN

package Elastic::Manual::Scoping;

# ABSTRACT: An optional in-memory cache, essential for keeping weak refs live

__END__

=pod

=encoding UTF-8

=head1 NAME

Elastic::Manual::Scoping - An optional in-memory cache, essential for keeping weak refs live

=head1 VERSION

version 0.52

=head1 Warning

Scoping is an advanced topic - don't worry about L<Elastic::Model::Scope> until
you need it.

=head1 USES FOR Elastic::Model::Scope

L<Elastic::Model::Scope> acts as an in-memory cache, and serves three
futher purposes:

=head2 Keep weak-ref Elastic::Doc attributes alive

If you have a C<$post> object which has a C<user> attribute, and a C<$user>
object with a C<posts> attribute, then you will want to make (eg) the
C<< $posts->user >> attribute a
L<weak ref|https://metacpan.org/module/Moose::Manual::Attributes#Weak-references>
to avoid circular references.

But then you would have a problem:

    sub add_post_to_user {
        my ( $domain, $user_id, $content )= @_;
        my $user = $domain->get( user => $user_id );
        my $post = $domain->create(
            post => {
                content => $content,
                user    => $user;
            }
        );
        $user->add_post($post);
        $user->save;
        return $post;
    }

    my $post = add_post_to_user($domain, 1234, 'my post content');

    print $post->user->name;
    # ERROR - user has disappeared!

B<Scopes keep all your doc class objects in scope, so that they don't disappear
out from under you>.

So this would work:

    my $post;
    {
        my $scope = $model->new_scope;
        $post = add_post_to_user($domain, 1234, 'my post content');

        print $post->user->name;
        # Clint

    }
    # $scope has now disappeared

    print $post->user->name;
    # ERROR - user has disappeared!

=head2 Reuse Elastic::Doc objects as singletons.

By default, each object is a singleton.  For instance, if you do:

    my $foo = $domain->get( user => 123 );
    my $bar = $domain->get( user => 123 );

    print $bar->name;
    # Clint

    $foo->name('John');

    print $bar->name;



( run in 0.829 second using v1.01-cache-2.11-cpan-39bf76dae61 )