root/branches/release-35/lib/MT/TemplateMap.pm @ 1957

Revision 1957, 8.9 kB (checked in by bchoate, 20 months ago)

Fixes for propogation of build_type from template to templatemaps. BugId:79370

  • Property svn:keywords set to Author Date Id Revision
Line 
1# Movable Type (r) Open Source (C) 2001-2008 Six Apart, Ltd.
2# This program is distributed under the terms of the
3# GNU General Public License, version 2.
4#
5# $Id$
6
7package MT::TemplateMap;
8
9use strict;
10use base qw( MT::Object );
11
12__PACKAGE__->install_properties({
13    column_defs => {
14        'id' => 'integer not null auto_increment',
15        'blog_id' => 'integer not null',
16        'template_id' => 'integer not null',
17        'archive_type' => 'string(25) not null',
18        'file_template' => 'string(255)',
19        'is_preferred' => 'boolean',
20        'build_type' => 'smallint',
21        'build_interval' => 'integer',
22    },
23    indexes => {
24        blog_id => 1,
25        template_id => 1,
26        archive_type => 1,
27        is_preferred => 1,
28    },
29    defaults => {
30        'build_type' => 1,
31    },
32    child_classes => ['MT::FileInfo'],
33    datasource => 'templatemap',
34    primary_key => 'id',
35    cacheable => 0,
36});
37
38sub class_label {
39    return MT->translate("Archive Mapping");
40}
41
42sub class_label_plural {
43    return MT->translate("Archive Mappings");
44}
45
46sub save {
47    my $map = shift;
48    my $res = $map->SUPER::save();
49    return $res unless $res;
50
51    my $at   = $map->archive_type;
52    my $blog = MT->model('blog')->load($map->blog_id)
53        or return;
54    my $blog_at   = $blog->archive_type;
55    my @ats = map { $_ } 
56        grep { $map->archive_type ne $_ }
57            split /,/, $blog_at
58                if $blog_at ne 'None';
59    push @ats, $map->archive_type;
60    my $new_at = join ',', @ats;
61    if ($new_at ne $blog_at) {
62        $blog->archive_type($new_at);
63        $blog->save;
64    }
65    return 1;
66}
67
68sub remove {
69    my $map = shift;
70    $map->remove_children({ key => 'templatemap_id' });
71    my $result = $map->SUPER::remove(@_);
72   
73    if (ref $map) {
74        my $remaining = MT::TemplateMap->load(
75          {
76            blog_id => $map->blog_id,
77            archive_type => $map->archive_type,
78            id => [ $map->id ],
79          },
80          {
81            limit => 1,
82            not => { id => 1 }
83          }
84        );
85        if ($remaining) {
86            $remaining->is_preferred(1);
87            $remaining->save;
88        }
89        else {
90            my $blog = MT->model('blog')->load($map->blog_id)
91                or return;
92            my $at   = $blog->archive_type;
93            if ( $at && $at ne 'None' ) {
94                my @newat = map { $_ } grep { $map->archive_type ne $_ } split /,/, $at;
95                $blog->archive_type(join ',', @newat);
96                $blog->save;
97            }
98        }
99    }
100    else {
101        my $maps_iter = MT::TemplateMap->count_group_by(
102            undef,
103            { group => [ 'blog_id', 'archive_type' ] }
104        );
105        my %ats;
106        while ( my ( $count, $blog_id, $at ) = $maps_iter->() ) {
107            my $ats = $ats{$blog_id};
108            push @$ats, $at if $count > 0;
109            $ats{$blog_id} = $ats;
110        }
111        my $iter = MT::Blog->load_iter();
112        while ( my $blog = $iter->() ) {
113            $blog->archive_type( $ats{ $blog->id } ? join ',', @{ $ats{ $blog->id } } : '' );
114            $blog->save;
115            for my $at ( @{ $ats{ $blog->id } } ) {
116                unless ( __PACKAGE__->exist({
117                    blog_id => $blog->id, archive_type => $at, is_preferred => 1 
118                }) ) {
119                    my $remaining = __PACKAGE__->load(
120                      {
121                        blog_id => $blog->id,
122                        archive_type => $at,
123                      },
124                      {
125                        limit => 1,
126                      }
127                    );
128                    if ($remaining) {
129                        $remaining->is_preferred(1);
130                        $remaining->save;
131                    }
132                }
133            }
134        }
135    }
136    $result;
137}
138
139sub prefer {
140    my $map = shift;
141    my ($prefer) = @_;
142    $prefer = (defined($prefer) && $prefer) ? 1 : 0;
143
144    if ($prefer) {
145        return 1 if $map->is_preferred;
146        my $preferred = MT::TemplateMap->load({
147                blog_id => $map->blog_id,
148                archive_type => $map->archive_type,
149                is_preferred => 1,
150            }) or return;
151        $preferred->is_preferred(0);
152        $preferred->save or return $map->error($preferred->errstr);
153        $map->is_preferred(1);
154        $map->save or return $map->error($map->errstr);
155    } else {
156        return 1 unless $map->is_preferred;
157        if ($map->_prefer_next_map) {
158            $map->is_preferred(0);
159            $map->save or return $map->error($map->errstr);
160        }
161    }
162}
163
164sub _prefer_next_map {
165    my $map = shift;
166    my @all = MT::TemplateMap->load({ blog_id => $map->blog_id,
167                                      archive_type => $map->archive_type });
168    @all = grep { $_->id != $map->id } @all;
169    if (@all) {
170        $all[0]->is_preferred(1);
171        $all[0]->save;
172        return 1;
173    }
174    return 0;
175}
176
1771;
178__END__
179
180=head1 NAME
181
182MT::TemplateMap - Movable Type archive-template association record
183
184=head1 SYNOPSIS
185
186    use MT::TemplateMap;
187    my $map = MT::TemplateMap->new;
188    $map->blog_id($tmpl->blog_id);
189    $map->template_id($tmpl->id);
190    $map->archive_type('Monthly');
191    $map->file_template('<$MTArchiveDate format="%Y/%m/index.html"$>');
192    $map->is_preferred(1);
193    $map->save
194        or die $map->errstr;
195
196=head1 DESCRIPTION
197
198An I<MT::TemplateMap> object represents a single association between an
199Archive Template and an archive type for a particular blog. For example, if
200you set up a template called C<Date-Based> and assign to the C<Monthly>
201archive type in your blog, such an association will be represented by one
202I<MT::TemplateMap> object.
203
204=head1 USAGE
205
206As a subclass of I<MT::Object>, I<MT::TemplateMap> inherits all of the
207data-management and -storage methods from that class; thus you should look
208at the I<MT::Object> documentation for details about creating a new object,
209loading an existing object, saving an object, etc.
210
211=head1 DATA ACCESS METHODS
212
213The I<MT::TemplateMap> object holds the following pieces of data. These
214fields can be accessed and set using the standard data access methods
215described in the I<MT::Object> documentation.
216
217=over 4
218
219=item * id
220
221The numeric ID of the template map record.
222
223=item * blog_id
224
225The numeric ID of the blog with which this template map record is associated.
226
227=item * template_id
228
229The numeric ID of the template.
230
231=item * archive_type
232
233The archive type; should be one of the following values: C<Individual>,
234C<Daily>, C<Weekly>, C<Monthly>, or C<Category>.
235
236=item * file_template
237
238The Archive File Template for this particular mapping; this defines the output
239files for the pages generated from the template for this archive type,
240using standard MT template tags.
241
242=item * is_preferred
243
244A boolean flag specifying whether this particular template is preferred over
245any others defined for this archive type. This is used when generating links
246to archives of this archive type--the link will always link to the preferred
247archive type.
248
249=back
250
251=head1 METHODS
252
253=over 4
254
255=item * save()
256
257Saves the object.  It also rearranges blog's archive type.  If the saved
258template map is new and there is no other template maps with the same
259archive type has been, the archive type is also added to the blog.
260
261=item * remove()
262
263Removes template maps specified in terms and args (if called as class method)
264or the template map (if called as instance method).  It also rearrange blog's
265archive types which are used to determine what types of archive will be
266published during rebuild.  If template map is removed and there remains no
267template map with the archive type, the archive type is removed from blog's
268archive types to be rebuilt.
269
270=item * prefer(boolean)
271
272Set the template map preferred or not, depending on the argument.  If the map
273has been preferred and is being unpreferred, and if there are any other
274I<MT::TemplateMap> objects defined for this particular archive type and blog,
275the first of the other objects will be set as the preferred object.
276Its I<is_preferred> flag will be set to true.  If the map is the only
277I<MT::TemplateMap> object for the blog and the archive type, the method does
278nothing - the map continues to be preferred.
279
280=back
281
282=head1 DATA LOOKUP
283
284In addition to numeric ID lookup, you can look up or sort records by any
285combination of the following fields. See the I<load> documentation in
286I<MT::Object> for more information.
287
288=over 4
289
290=item * blog_id
291
292=item * template_id
293
294=item * archive_type
295
296=item * is_preferred
297
298=back
299
300=head1 NOTES
301
302=over 4
303
304=item * $obj->remove()
305
306When you remove a I<MT::TemplateMap> object using I<MT::TemplateMap::remove>,
307if the I<$map> object you are removing has the I<is_preferred> flag set to
308true, and if there are any other I<MT::TemplateMap> objects defined for this
309particular archive type and blog, the first of the other objects will be
310set as the preferred object. Its I<is_preferred> flag will be set to true.
311
312=back
313
314=head1 AUTHOR & COPYRIGHT
315
316Please see L<MT/AUTHOR & COPYRIGHT>.
317
318=cut
Note: See TracBrowser for help on using the browser.