cleanup modelines
[dbsrgits/DBIx-Class-DeploymentHandler.git] / lib / DBIx / Class / DeploymentHandler / HandlesVersioning.pm
1 package DBIx::Class::DeploymentHandler::HandlesVersioning;
2 use Moose::Role;
3
4 # note: the sets returned need to match!
5 requires 'next_version_set';
6 requires 'previous_version_set';
7
8 1;
9
10 # vim: ts=2 sw=2 expandtab
11
12 __END__
13
14 =head1 DESCRIPTION
15
16 Typically a VersionHandler will take a C<to_version> and yeild an iterator of
17 "version sets."
18
19 A "version set" could be defined as:
20
21  subtype 'Version', as 'Str';
22  subtype 'VersionSet', as 'ArrayRef[Str]';
23
24 and all a "version set" does is uniquely identify a migration.
25
26 Typically a call to a VersionHandler's L</next_version_set> with a C<db_version>
27 of 1 and a C<to_version> of 5 will iterate over something like the following:
28
29  [1, 2]
30  [2, 3]
31  [3, 4]
32  [4, 5]
33  undef
34
35 or maybe just
36
37  [1, 5]
38  undef
39
40 Really how the version sets are arranged is up to the VersionHandler being
41 used.
42
43 In some cases users will not want versions to have inherent "previous
44 versions," which is why the version set is an C<ArrayRef>.  In those cases the
45 user should opt to returning merely the version that the database is being
46 upgraded to in each step.
47
48 One idea that has been suggested to me has been to have a form of dependency
49 management of the database "versions."  In this case the versions are actually
50 more like features that may or may not be applied.  For example, one might
51 start with version 1 and have a feature (version) C<users>.
52
53 Each feature might require that the database be upgraded to another version
54 first.  If one were to implement a system like this, here is how the
55 VersionHandler's L</next_version_set> might look.
56
57  to_version = "users", db_version = 1
58  [3]
59  [5]
60  ["users"]
61  undef
62
63 So what just happened there is that C<users> depends on version 5, which depends
64 on version 3, which depends on version 1, which is already installed.  To be
65 clear, the reason we use single versions instead of version pairs is because
66 there is no inherent order for this type of database upgraded.
67
68 =head2 Downgrades
69
70 For the typical case I'd like downgrades to be easy for users to perform and
71 understand.  That means that with the first two examples give above we can use
72 the L</previous_version_set> iterator to yeild the following:
73
74
75  db_version = 5, to_version=1
76  [4, 5]
77  [3, 4]
78  [2, 3]
79  [1, 2]
80  undef
81
82 or maybe just
83
84  [1, 5]
85  undef
86
87 Note that we do not swap the version number order.  This allows us to remain
88 consistent in our version set abstraction, since a version set really just
89 describes a version change, and not necesarily a defined progression.
90
91 =method next_version_set
92
93  print 'versions to install: ';
94  while (my $vs = $dh->next_version_set) {
95    print join q(, ), @{$vs}
96  }
97  print qq(\n);
98
99 return an arrayref describing each version that needs to be
100 installed to upgrade to C<< $dh->to_version >>.
101
102 =method previous_version_set
103
104  print 'versions to uninstall: ';
105  while (my $vs = $dh->previous_version_set) {
106    print join q(, ), @{$vs}
107  }
108  print qq(\n);
109
110 return an arrayref describing each version that needs to be
111 "installed" to downgrade to C<< $dh->to_version >>.
112
113 =head1 KNOWN IMPLEMENTATIONS
114
115 =over
116
117 =item *
118
119 L<DBIx::Class::DeploymentHandler::VersionHandler::Monotonic>
120
121 =item *
122
123 L<DBIx::Class::DeploymentHandler::VersionHandler::DatabaseToSchemaVersions>
124
125 =item *
126
127 L<DBIx::Class::DeploymentHandler::VersionHandler::ExplicitVersions>
128
129 =back
130