~kosova/+junk/tuxfamily-twiki

« back to all changes in this revision

Viewing changes to foswiki/lib/Foswiki/UI/Save.pm

  • Committer: James Michael DuPont
  • Date: 2009-07-18 19:58:49 UTC
  • Revision ID: jamesmikedupont@gmail.com-20090718195849-vgbmaht2ys791uo2
added foswiki

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
# See bottom of file for license and copyright information
 
2
 
 
3
=begin TML
 
4
 
 
5
---+ package Foswiki::UI::Save
 
6
 
 
7
UI delegate for save function
 
8
 
 
9
=cut
 
10
 
 
11
package Foswiki::UI::Save;
 
12
 
 
13
use strict;
 
14
use Error qw( :try );
 
15
use Assert;
 
16
 
 
17
require Foswiki;
 
18
require Foswiki::UI;
 
19
require Foswiki::Meta;
 
20
require Foswiki::OopsException;
 
21
 
 
22
# Used by save and preview
 
23
sub buildNewTopic {
 
24
    my ( $session, $script ) = @_;
 
25
 
 
26
    my $query    = $session->{request};
 
27
    my $webName  = $session->{webName};
 
28
    my $topic    = $session->{topicName};
 
29
    my $store    = $session->{store};
 
30
    my $revision = $query->param('rev') || undef;
 
31
 
 
32
    unless ( scalar( $query->param() ) ) {
 
33
 
 
34
        # insufficient parameters to save
 
35
        throw Foswiki::OopsException(
 
36
            'attention',
 
37
            def    => 'bad_script_parameters',
 
38
            web    => $session->{webName},
 
39
            topic  => $session->{topicName},
 
40
            params => [$script]
 
41
        );
 
42
    }
 
43
 
 
44
    Foswiki::UI::checkWebExists( $session, $webName, $topic, 'save' );
 
45
 
 
46
    my $topicExists = $store->topicExists( $webName, $topic );
 
47
 
 
48
    # Prevent saving existing topic?
 
49
    my $onlyNewTopic = Foswiki::isTrue( $query->param('onlynewtopic') );
 
50
    if ( $onlyNewTopic && $topicExists ) {
 
51
 
 
52
        # Topic exists and user requested oops if it exists
 
53
        throw Foswiki::OopsException(
 
54
            'attention',
 
55
            def   => 'topic_exists',
 
56
            web   => $webName,
 
57
            topic => $topic
 
58
        );
 
59
    }
 
60
 
 
61
    # prevent non-Wiki names?
 
62
    my $onlyWikiName = Foswiki::isTrue( $query->param('onlywikiname') );
 
63
    if (   ($onlyWikiName)
 
64
        && ( !$topicExists )
 
65
        && ( !Foswiki::isValidTopicName($topic) ) )
 
66
    {
 
67
 
 
68
        # do not allow non-wikinames
 
69
        throw Foswiki::OopsException(
 
70
            'attention',
 
71
            def    => 'not_wikiword',
 
72
            web    => $webName,
 
73
            topic  => $topic,
 
74
            params => [$topic]
 
75
        );
 
76
    }
 
77
 
 
78
    my $user = $session->{user};
 
79
    Foswiki::UI::checkAccess( $session, $webName, $topic, 'CHANGE', $user );
 
80
 
 
81
    my $saveOpts = {};
 
82
    $saveOpts->{minor} = 1 if $query->param('dontnotify');
 
83
    my $originalrev = $query->param('originalrev');    # rev edit started on
 
84
 
 
85
    # Populate the new meta data
 
86
    my $newMeta = new Foswiki::Meta( $session, $webName, $topic );
 
87
 
 
88
    my ( $prevMeta,     $prevText );
 
89
    my ( $templateText, $templateMeta );
 
90
    my $templatetopic = $query->param('templatetopic');
 
91
    my $templateweb   = $webName;
 
92
 
 
93
    if ($templatetopic) {
 
94
        ( $templateweb, $templatetopic ) =
 
95
          $session->normalizeWebTopicName( $templateweb, $templatetopic );
 
96
 
 
97
        if ( $store->topicExists( $templateweb, $templatetopic ) ) {
 
98
            # Validated
 
99
            $templateweb =
 
100
              Foswiki::Sandbox::untaintUnchecked( $templateweb );
 
101
            $templatetopic =
 
102
              Foswiki::Sandbox::untaintUnchecked( $templatetopic );
 
103
        } else {
 
104
            throw Foswiki::OopsException(
 
105
                'attention',
 
106
                def   => 'no_such_topic_template',
 
107
                web   => $templateweb,
 
108
                topic => $templatetopic
 
109
            );
 
110
        }
 
111
    }
 
112
 
 
113
    if ($topicExists) {
 
114
        ( $prevMeta, $prevText ) =
 
115
          $store->readTopic( $user, $webName, $topic, $revision );
 
116
        if ($prevMeta) {
 
117
            foreach my $k ( keys %$prevMeta ) {
 
118
                unless ( $k =~ /^_/
 
119
                    || $k eq 'FORM'
 
120
                    || $k eq 'TOPICPARENT'
 
121
                    || $k eq 'FIELD' )
 
122
                {
 
123
                    $newMeta->copyFrom( $prevMeta, $k );
 
124
                }
 
125
            }
 
126
        }
 
127
    }
 
128
    elsif ($templatetopic) {
 
129
        ( $templateMeta, $templateText ) =
 
130
          $store->readTopic( $user, $templateweb, $templatetopic, $revision );
 
131
        $templateText = '' if $query->param('newtopic');    # created by edit
 
132
        $templateText =
 
133
          $session->expandVariablesOnTopicCreation( $templateText, $user,
 
134
            $webName, $topic );
 
135
        foreach my $k ( keys %$templateMeta ) {
 
136
            unless ( $k =~ /^_/
 
137
                || $k eq 'FORM'
 
138
                || $k eq 'TOPICPARENT'
 
139
                || $k eq 'FIELD'
 
140
                || $k eq 'TOPICMOVED' )
 
141
            {
 
142
                $newMeta->copyFrom( $templateMeta, $k );
 
143
            }
 
144
        }
 
145
 
 
146
        # topic creation, there is no original rev
 
147
        $originalrev = 0;
 
148
    }
 
149
 
 
150
    # Determine the new text
 
151
    my $newText = $query->param('text');
 
152
 
 
153
    my $forceNewRev = $query->param('forcenewrevision');
 
154
    $saveOpts->{forcenewrevision} = $forceNewRev;
 
155
    my $newParent = $query->param('topicparent');
 
156
 
 
157
    if ( defined($newText) ) {
 
158
 
 
159
        # text is defined in the query, save that text
 
160
        $newText =~ s/\r//g;
 
161
        $newText .= "\n" unless $newText =~ /\n$/s;
 
162
 
 
163
    }
 
164
    elsif ( defined $templateText ) {
 
165
 
 
166
        # no text in the query, but we have a templatetopic
 
167
        $newText     = $templateText;
 
168
        $originalrev = 0;               # disable merge
 
169
 
 
170
    }
 
171
    else {
 
172
        $newText = '';
 
173
        if ( defined $prevText ) {
 
174
            $newText     = $prevText;
 
175
            $originalrev = 0;           # disable merge
 
176
        }
 
177
    }
 
178
 
 
179
    my $mum;
 
180
    if ($newParent) {
 
181
        if ( $newParent ne 'none' ) {
 
182
            $mum = { 'name' => $newParent };
 
183
        }
 
184
    }
 
185
    elsif ($templateMeta) {
 
186
        $mum = $templateMeta->get('TOPICPARENT');
 
187
    }
 
188
    elsif ($prevMeta) {
 
189
        $mum = $prevMeta->get('TOPICPARENT');
 
190
    }
 
191
    $newMeta->put( 'TOPICPARENT', $mum ) if $mum;
 
192
 
 
193
    my $formName = $query->param('formtemplate');
 
194
    my $formDef;
 
195
    my $copyMeta;
 
196
 
 
197
    if ($formName) {
 
198
 
 
199
        # new form, default field values will be null
 
200
        $formName = '' if ( $formName eq 'none' );
 
201
    }
 
202
    elsif ($templateMeta) {
 
203
 
 
204
        # populate the meta-data with field values from the template
 
205
        $formName = $templateMeta->get('FORM');
 
206
        $formName = $formName->{name} if $formName;
 
207
        $copyMeta = $templateMeta;
 
208
    }
 
209
    elsif ($prevMeta) {
 
210
 
 
211
        # populate the meta-data with field values from the existing topic
 
212
        $formName = $prevMeta->get('FORM');
 
213
        $formName = $formName->{name} if $formName;
 
214
        $copyMeta = $prevMeta;
 
215
    }
 
216
 
 
217
    if ($formName) {
 
218
        require Foswiki::Form;
 
219
        $formDef = new Foswiki::Form( $session, $webName, $formName );
 
220
        unless ($formDef) {
 
221
            unless ($prevMeta) {
 
222
                throw Foswiki::OopsException(
 
223
                    'attention',
 
224
                    def    => 'no_form_def',
 
225
                    web    => $session->{webName},
 
226
                    topic  => $session->{topicName},
 
227
                    params => [ $webName, $formName ]
 
228
                );
 
229
            }
 
230
 
 
231
            # Recreate the form fields from the previous rev of the topic.
 
232
            $formDef =
 
233
              new Foswiki::Form( $session, $webName, $formName, $prevMeta );
 
234
        }
 
235
        $newMeta->put( 'FORM', { name => $formName } );
 
236
    }
 
237
    if ( $copyMeta && $formDef ) {
 
238
 
 
239
        # Copy existing fields into new form, filtering on the
 
240
        # known field names so we don't copy dead data. Though we
 
241
        # really should, of course. That comes later.
 
242
        my $filter = join( '|',
 
243
            map    { $_->{name} }
 
244
              grep { $_->{name} } @{ $formDef->getFields() } );
 
245
        $newMeta->copyFrom( $copyMeta, 'FIELD', qr/^($filter)$/ );
 
246
    }
 
247
    if ($formDef) {
 
248
 
 
249
        # override with values from the query
 
250
        my ( $seen, $missing ) =
 
251
          $formDef->getFieldValuesFromQuery( $query, $newMeta );
 
252
        if ( $seen && @$missing ) {
 
253
 
 
254
            # chuck up if there is at least one field value defined in the
 
255
            # query and a mandatory field was not defined in the
 
256
            # query or by an existing value.
 
257
            # Item5428: clean up <nop>'s
 
258
            @$missing = map {
 
259
                s/<nop>//g;
 
260
                $_
 
261
            } @$missing;
 
262
            throw Foswiki::OopsException(
 
263
                'attention',
 
264
                def    => 'mandatory_field',
 
265
                web    => $session->{webName},
 
266
                topic  => $session->{topicName},
 
267
                params => [ join( ' ', @$missing ) ]
 
268
            );
 
269
        }
 
270
    }
 
271
 
 
272
    my $merged;
 
273
 
 
274
    # If the topic exists, see if we need to merge
 
275
    if ( $topicExists && $originalrev ) {
 
276
        my ( $orev, $odate );
 
277
        if ( $originalrev =~ /^(\d+)_(\d+)$/ ) {
 
278
            ( $orev, $odate ) = ( $1, $2 );
 
279
        }
 
280
        elsif ( $originalrev =~ /^\d+$/ ) {
 
281
            $orev = $originalrev;
 
282
        }
 
283
        else {
 
284
            $orev = 0;
 
285
        }
 
286
        my ( $date, $author, $rev, $comment ) = $newMeta->getRevisionInfo();
 
287
 
 
288
        # If the last save was by me, don't merge
 
289
        if ( ( $orev ne $rev || $odate && $date && $odate ne $date )
 
290
            && $author ne $user )
 
291
        {
 
292
 
 
293
            require Foswiki::Merge;
 
294
 
 
295
            my $pti = $prevMeta->get('TOPICINFO');
 
296
            if (   $pti
 
297
                && $pti->{reprev}
 
298
                && $pti->{version}
 
299
                && $pti->{reprev} == $pti->{version} )
 
300
            {
 
301
 
 
302
                # If the ancestor revision was generated by a reprev,
 
303
                # then the original is lost and we can't 3-way merge
 
304
 
 
305
                $session->{plugins}
 
306
                  ->dispatch( 'beforeMergeHandler', $newText, $pti->{version},
 
307
                    $prevText, undef, undef, $webName, $topic );
 
308
 
 
309
                $newText =
 
310
                  Foswiki::Merge::merge2( $pti->{version}, $prevText, $rev,
 
311
                    $newText, '.*?\n', $session );
 
312
            }
 
313
            else {
 
314
 
 
315
                # common ancestor; we can 3-way merge
 
316
                my ( $ancestorMeta, $ancestorText ) =
 
317
                  $store->readTopic( undef, $webName, $topic, $orev );
 
318
 
 
319
                $session->{plugins}
 
320
                  ->dispatch( 'beforeMergeHandler', $newText, $rev, $prevText,
 
321
                    $orev, $ancestorText, $webName, $topic );
 
322
 
 
323
                $newText =
 
324
                  Foswiki::Merge::merge3( $orev, $ancestorText, $rev, $prevText,
 
325
                    'new', $newText, '.*?\n', $session );
 
326
            }
 
327
            if ( $formDef && $prevMeta ) {
 
328
                $newMeta->merge( $prevMeta, $formDef );
 
329
            }
 
330
            $merged =
 
331
              [ $orev, $session->{users}->getWikiName($author), $rev || 1 ];
 
332
        }
 
333
    }
 
334
 
 
335
    return ( $newMeta, $newText, $saveOpts, $merged );
 
336
}
 
337
 
 
338
=begin TML
 
339
 
 
340
---++ StaticMethod save($session)
 
341
 
 
342
Command handler for =save= command.
 
343
This method is designed to be
 
344
invoked via the =UI::run= method.
 
345
 
 
346
See System.CommandAndCGIScripts for details of parameters.
 
347
 
 
348
Note: =cmd= has been deprecated in favour of =action=. It will be deleted at
 
349
some point.
 
350
 
 
351
=cut
 
352
 
 
353
sub save {
 
354
    my $session = shift;
 
355
 
 
356
    my $query = $session->{request};
 
357
    my $web   = $session->{webName};
 
358
    my $topic = $session->{topicName};
 
359
    my $store = $session->{store};
 
360
    my $user  = $session->{user};
 
361
 
 
362
    # Do not remove, keep as undocumented feature for compatibility with
 
363
    # TWiki 4.0.x: Allow for dynamic topic creation by replacing strings
 
364
    # of at least 10 x's XXXXXX with a next-in-sequence number.
 
365
    # See Codev.AllowDynamicTopicNameCreation
 
366
    if ( $topic =~ /X{10}/ ) {
 
367
        my $n         = 0;
 
368
        my $baseTopic = $topic;
 
369
        $store->clearLease( $web, $baseTopic );
 
370
        do {
 
371
            $topic = $baseTopic;
 
372
            $topic =~ s/X{10}X*/$n/e;
 
373
            $n++;
 
374
        } while ( $store->topicExists( $web, $topic ) );
 
375
        $session->{topicName} = $topic;
 
376
    }
 
377
 
 
378
    # Allow for more flexible topic creation with sortable names and
 
379
    # better performance. See Codev.AutoIncTopicNameOnSave
 
380
    if ( $topic =~ /AUTOINC([0-9]+)/ ) {
 
381
        my $start     = $1;
 
382
        my $baseTopic = $topic;
 
383
        $store->clearLease( $web, $baseTopic );
 
384
        my $nameFilter = $topic;
 
385
        $nameFilter =~ s/AUTOINC([0-9]+)/([0-9]+)/;
 
386
        my @list =
 
387
          sort { $a <=> $b }
 
388
          map { s/^$nameFilter$/$1/; s/^0*([0-9])/$1/; $_ }
 
389
          grep { /^$nameFilter$/ } $store->getTopicNames($web);
 
390
        if ( scalar @list ) {
 
391
 
 
392
            # find last one, and increment by one
 
393
            my $next = $list[$#list] + 1;
 
394
            my $len  = length($start);
 
395
            $start =~ s/^0*([0-9])/$1/;    # cut leading zeros
 
396
            $next = $start if ( $start > $next );
 
397
            my $pad = $len - length($next);
 
398
            if ( $pad > 0 ) {
 
399
                $next = '0' x $pad . $next;    # zero-pad
 
400
            }
 
401
            $topic =~ s/AUTOINC[0-9]+/$next/;
 
402
        }
 
403
        else {
 
404
 
 
405
            # first auto-inc topic
 
406
            $topic =~ s/AUTOINC[0-9]+/$start/;
 
407
        }
 
408
        $session->{topicName} = $topic;
 
409
    }
 
410
 
 
411
    my $saveaction = '';
 
412
    foreach my $action qw( save checkpoint quietsave cancel preview
 
413
      addform replaceform delRev repRev ) {
 
414
        if ( $query->param( 'action_' . $action ) )
 
415
        {
 
416
            $saveaction = $action;
 
417
            last;
 
418
        }
 
419
      }
 
420
 
 
421
      # the 'action' parameter has been deprecated, though is still available
 
422
      # for compatibility with old templates.
 
423
      if ( !$saveaction && $query->param('action') ) {
 
424
        $saveaction = lc( $query->param('action') );
 
425
        $session->logger->log('warning',<<WARN);
 
426
Use of deprecated "action" parameter to "save". Correct your templates!
 
427
WARN
 
428
 
 
429
        # handle old values for form-related actions:
 
430
        $saveaction = 'addform'     if ( $saveaction eq 'add form' );
 
431
        $saveaction = 'replaceform' if ( $saveaction eq 'replace form...' );
 
432
    }
 
433
 
 
434
    if ( $saveaction eq 'cancel' ) {
 
435
        my $lease = $store->getLease( $web, $topic );
 
436
        if ( $lease && $lease->{user} eq $user ) {
 
437
            $store->clearLease( $web, $topic );
 
438
        }
 
439
 
 
440
        # redirect to a sensible place (a topic that exists)
 
441
        my ( $w, $t ) = ( '', '' );
 
442
        foreach my $test ( $topic, $query->param('topicparent'),
 
443
            $Foswiki::cfg{HomeTopicName} )
 
444
        {
 
445
            ( $w, $t ) = $session->normalizeWebTopicName( $web, $test );
 
446
            last if ( $store->topicExists( $w, $t ) );
 
447
        }
 
448
        my $viewURL = $session->getScriptUrl( 1, 'view', $w, $t );
 
449
        $session->redirect( $session->redirectto($viewURL) );
 
450
 
 
451
        return;
 
452
    }
 
453
 
 
454
    if ( $saveaction eq 'preview' ) {
 
455
        require Foswiki::UI::Preview;
 
456
        Foswiki::UI::Preview::preview($session);
 
457
        return;
 
458
    }
 
459
 
 
460
    # Do this *before* we do any query parameter rewriting
 
461
    Foswiki::UI::checkValidationKey($session, 'save', $web, $topic);
 
462
 
 
463
    my $editaction = lc( $query->param('editaction') ) || '';
 
464
    my $edit       = $query->param('edit')             || 'edit';
 
465
    my $editparams = $query->param('editparams')       || '';
 
466
 
 
467
    ## SMELL: The form affecting actions do not preserve edit and editparams
 
468
    if (   $saveaction eq 'addform'
 
469
        || $saveaction eq 'replaceform'
 
470
        || $saveaction eq 'preview' && $query->param('submitChangeForm') )
 
471
    {
 
472
        require Foswiki::UI::ChangeForm;
 
473
        $session->writeCompletePage(
 
474
            Foswiki::UI::ChangeForm::generate(
 
475
                $session, $web, $topic, $editaction
 
476
            )
 
477
        );
 
478
        return;
 
479
    }
 
480
 
 
481
    my $redirecturl;
 
482
 
 
483
    if ( $saveaction eq 'checkpoint' ) {
 
484
        $query->param( -name => 'dontnotify', -value => 'checked' );
 
485
        my $edittemplate = $query->param( 'template' );
 
486
        my $editURL = $session->getScriptUrl( 1, $edit, $web, $topic );
 
487
        $redirecturl = $editURL . '?t=' . time();
 
488
        $redirecturl .= '&redirectto=' . $query->param('redirectto')
 
489
          if $query->param('redirectto');
 
490
 
 
491
        # select the appropriate edit template
 
492
        $redirecturl .= '&action=' . $editaction if $editaction;
 
493
        $redirecturl .= '&template=' . $edittemplate if $edittemplate;
 
494
 
 
495
        $redirecturl .= '&skin=' . $query->param('skin')
 
496
          if $query->param('skin');
 
497
        $redirecturl .= '&cover=' . $query->param('cover')
 
498
          if $query->param('cover');
 
499
        $redirecturl .= '&nowysiwyg=' . $query->param('nowysiwyg')
 
500
          if $query->param('nowysiwyg');
 
501
        $redirecturl .= '&action=' . $query->param('action')
 
502
          if $query->param('action');
 
503
        $redirecturl .= $editparams
 
504
          if $editparams;    # May contain anchor
 
505
        my $lease = $store->getLease( $web, $topic );
 
506
        if ( $lease && $lease->{user} eq $user ) {
 
507
            $store->setLease( $web, $topic, $user, $Foswiki::cfg{LeaseLength} );
 
508
        }
 
509
 
 
510
        # drop through
 
511
    } else {
 
512
         $redirecturl = $session->getScriptUrl( 1, 'view', $web, $topic );
 
513
     }
 
514
 
 
515
    # Do we have ?redirectto=
 
516
    if ($saveaction ne 'checkpoint') {
 
517
        $redirecturl = $session->redirectto($redirecturl);
 
518
    }
 
519
 
 
520
    if ( $saveaction eq 'quietsave' ) {
 
521
        $query->param( -name => 'dontnotify', -value => 'checked' );
 
522
        $saveaction = 'save';
 
523
 
 
524
        # drop through
 
525
    }
 
526
 
 
527
    if ( $saveaction =~ /^(del|rep)Rev$/ ) {
 
528
 
 
529
        # hidden, largely undocumented functions, used by administrators for
 
530
        # reverting spammed topics. These functions support rewriting
 
531
        # history, in a Joe Stalin kind of way. They should be replaced with
 
532
        # mechanisms for hiding revisions.
 
533
        $query->param( -name => 'cmd', -value => $saveaction );
 
534
 
 
535
        # drop through
 
536
    }
 
537
 
 
538
    my $saveCmd = $query->param('cmd') || 0;
 
539
    if ( $saveCmd && !$session->{users}->isAdmin( $session->{user} ) ) {
 
540
        throw Foswiki::OopsException(
 
541
            'accessdenied', status => 403,
 
542
            def    => 'only_group',
 
543
            web    => $web,
 
544
            topic  => $topic,
 
545
            params => [ $Foswiki::cfg{SuperAdminGroup} ]
 
546
        );
 
547
    }
 
548
 
 
549
    #success - redirect to topic view (unless its a checkpoint save)
 
550
 
 
551
    if ( $saveCmd eq 'delRev' ) {
 
552
 
 
553
        # delete top revision
 
554
        try {
 
555
            $store->delRev( $user, $web, $topic );
 
556
        }
 
557
        catch Error::Simple with {
 
558
            throw Foswiki::OopsException(
 
559
                'attention',
 
560
                def    => 'save_error',
 
561
                web    => $web,
 
562
                topic  => $topic,
 
563
                params => [ shift->{-text} ]
 
564
            );
 
565
        };
 
566
 
 
567
        $session->redirect( $redirecturl );
 
568
        return;
 
569
    }
 
570
 
 
571
    if ( $saveCmd eq 'repRev' ) {
 
572
 
 
573
        # replace top revision with the text from the query, trying to
 
574
        # make it look as much like the original as possible. The query
 
575
        # text is expected to contain %META as well as text.
 
576
        my $meta =
 
577
          new Foswiki::Meta( $session, $web, $topic, $query->param('text') );
 
578
        my $saveOpts = {
 
579
            timetravel => 1,
 
580
            operation  => 'cmd',
 
581
        };
 
582
 
 
583
        try {
 
584
            $store->repRev( $user, $web, $topic, $meta->text(), $meta,
 
585
                $saveOpts );
 
586
        }
 
587
        catch Error::Simple with {
 
588
            throw Foswiki::OopsException(
 
589
                'attention',
 
590
                def    => 'save_error',
 
591
                web    => $web,
 
592
                topic  => $topic,
 
593
                params => [ shift->{-text} ]
 
594
            );
 
595
        };
 
596
 
 
597
        $session->redirect( $redirecturl);
 
598
        return;
 
599
    }
 
600
 
 
601
    my ( $newMeta, $newText, $saveOpts, $merged ) =
 
602
      buildNewTopic( $session, 'save' );
 
603
 
 
604
    if ( $saveaction =~ /^(save|checkpoint)$/ ) {
 
605
        $session->{plugins}
 
606
          ->dispatch( 'afterEditHandler', $newText, $topic, $web, $newMeta );
 
607
    }
 
608
 
 
609
    try {
 
610
        $store->saveTopic( $user, $web, $topic, $newText, $newMeta, $saveOpts );
 
611
    }
 
612
    catch Error::Simple with {
 
613
        throw Foswiki::OopsException(
 
614
            'attention',
 
615
            def    => 'save_error',
 
616
            web    => $web,
 
617
            topic  => $topic,
 
618
            params => [ shift->{-text} ]
 
619
        );
 
620
    };
 
621
 
 
622
    my $lease = $store->getLease( $web, $topic );
 
623
 
 
624
    # clear the lease, if (and only if) we own it
 
625
    if ( $lease && $lease->{user} eq $user ) {
 
626
        $store->clearLease( $web, $topic );
 
627
    }
 
628
 
 
629
    if ($merged) {
 
630
        throw Foswiki::OopsException(
 
631
            'attention', status => 200,
 
632
            def    => 'merge_notice',
 
633
            web    => $web,
 
634
            topic  => $topic,
 
635
            params => $merged
 
636
        );
 
637
    }
 
638
 
 
639
    $session->redirect( $redirecturl );
 
640
}
 
641
 
 
642
1;
 
643
__DATA__
 
644
# Module of Foswiki - The Free and Open Source Wiki, http://foswiki.org/
 
645
#
 
646
# Copyright (C) 2008-2009 Foswiki Contributors. Foswiki Contributors
 
647
# are listed in the AUTHORS file in the root of this distribution.
 
648
# NOTE: Please extend that file, not this notice.
 
649
#
 
650
# Additional copyrights apply to some or all of the code in this
 
651
# file as follows:
 
652
#
 
653
# Copyright (C) 1999-2007 Peter Thoeny, peter@thoeny.org
 
654
# and TWiki Contributors. All Rights Reserved. TWiki Contributors
 
655
# are listed in the AUTHORS file in the root of this distribution.
 
656
# Based on parts of Ward Cunninghams original Wiki and JosWiki.
 
657
# Copyright (C) 1998 Markus Peter - SPiN GmbH (warpi@spin.de)
 
658
# Some changes by Dave Harris (drh@bhresearch.co.uk) incorporated
 
659
#
 
660
# This program is free software; you can redistribute it and/or
 
661
# modify it under the terms of the GNU General Public License
 
662
# as published by the Free Software Foundation; either version 2
 
663
# of the License, or (at your option) any later version. For
 
664
# more details read LICENSE in the root of this distribution.
 
665
#
 
666
# This program is distributed in the hope that it will be useful,
 
667
# but WITHOUT ANY WARRANTY; without even the implied warranty of
 
668
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
 
669
#
 
670
# As per the GPL, removal of this notice is prohibited.