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