working downgrades!
[dbsrgits/DBIx-Class-DeploymentHandler.git] / lib / DBIx / Class / DeploymentHandler / VersionHandler / ExplicitVersions.pm
1 package DBIx::Class::DeploymentHandler::VersionHandler::ExplicitVersions;
2 use Moose;
3 use Carp 'croak';
4
5 with 'DBIx::Class::DeploymentHandler::HandlesVersioning';
6
7 has schema_version => (
8   isa      => 'Str',
9   is       => 'ro',
10   required => 1,
11 );
12
13 has database_version => (
14   isa      => 'Str',
15   is       => 'ro',
16   required => 1,
17 );
18
19 has to_version => ( # configuration
20   is         => 'ro',
21   lazy_build => 1, # builder comes from another role...
22                    # which is... probably not how we want it
23 );
24
25 sub _build_to_version { $_[0]->schema_version }
26
27 has ordered_versions => (
28   is       => 'ro',
29   isa      => 'ArrayRef',
30   required => 1,
31   trigger  => sub {
32     my $to_version = $_[0]->to_version;
33     my $db_version = $_[0]->database_version;
34
35     croak 'to_version not in ordered_versions'
36       unless grep { $to_version eq $_ } @{ $_[1] };
37
38     croak 'database_version not in ordered_versions'
39       unless grep { $db_version eq $_ } @{ $_[1] };
40
41     for (@{ $_[1] }) {
42       return if $_ eq $db_version;
43       croak 'to_version is before database version in ordered_versions'
44         if $_ eq $to_version;
45     }
46   },
47 );
48
49 has _version_idx => (
50   is         => 'rw',
51   isa        => 'Int',
52   lazy_build => 1,
53 );
54
55 sub _inc_version_idx { $_[0]->_version_idx($_[0]->_version_idx + 1 ) }
56 sub _dec_version_idx { $_[0]->_version_idx($_[0]->_version_idx - 1 ) }
57
58 sub _build__version_idx {
59   my $self = shift;
60   my $start = $self->database_version;
61   my $idx = 0;
62   for (@{$self->ordered_versions}) {
63     return $idx
64       if $_ eq $self->database_version;
65     $idx++;
66   }
67 }
68
69 sub next_version_set {
70   my $self = shift;
71   return undef
72     if $self->ordered_versions->[$self->_version_idx] eq $self->to_version;
73
74   # this should never get in infinite loops because we ensure
75   # that the database version is in the list in the version_idx
76   # builder
77   my $next_idx = $self->_inc_version_idx;
78   return [
79     $self->ordered_versions->[$next_idx - 1],
80     $self->ordered_versions->[$next_idx    ],
81   ];
82 }
83
84 sub previous_version_set {
85   my $self = shift;
86   return undef
87     if $self->ordered_versions->[$self->_version_idx] eq $self->database_version;
88
89   # this should never get in infinite loops because we ensure
90   # that the database version is in the list in the version_idx
91   # builder
92   my $next_idx = $self->_dec_version_idx;
93   return [
94     $self->ordered_versions->[$next_idx - 1],
95     $self->ordered_versions->[$next_idx    ],
96   ];
97 }
98
99 __PACKAGE__->meta->make_immutable;
100
101 1;
102
103 __END__
104
105 vim: ts=2 sw=2 expandtab