View | Details | Raw Unified | Return to bug 29924
Collapse All | Expand All

(-)a/C4/Auth.pm (+31 lines)
Lines 278-283 sub get_template_and_user { Link Here
278
            # FIXME What to do if $patron does not exist?
278
            # FIXME What to do if $patron does not exist?
279
        }
279
        }
280
280
281
        if ($patron->password_expired) {
282
            my $reset_template_name = ( $in->{type} eq 'opac' ) ? 'opac-auth.tt' : 'auth.tt';
283
            $template = C4::Templates::gettemplate( $reset_template_name, $in->{type},
284
                $in->{query} );
285
            $cookie = $in->{query}->cookie(
286
                -name     => 'CGISESSID',
287
                -value    => '',
288
                -expires  => '',
289
                -HttpOnly => 1,
290
                -secure => ( C4::Context->https_enabled() ? 1 : 0 ),
291
            );
292
293
            $template->param(
294
                loginprompt => 1,
295
                login => 1,
296
                password_has_expired => 1,
297
                script_name => get_script_name(),
298
            );
299
300
            print $in->{query}->header(
301
                {
302
                    type              => 'text/html',
303
                    charset           => 'utf-8',
304
                    cookie            => $cookie,
305
                    'X-Frame-Options' => 'SAMEORIGIN'
306
                }
307
              ),
308
              $template->output;
309
            safe_exit;
310
        }
311
281
        # user info
312
        # user info
282
        $template->param( loggedinusername   => $user ); # OBSOLETE - Do not reuse this in template, use logged_in_user.userid instead
313
        $template->param( loggedinusername   => $user ); # OBSOLETE - Do not reuse this in template, use logged_in_user.userid instead
283
        $template->param( loggedinusernumber => $borrowernumber ); # FIXME Should be replaced with logged_in_user.borrowernumber
314
        $template->param( loggedinusernumber => $borrowernumber ); # FIXME Should be replaced with logged_in_user.borrowernumber
(-)a/Koha/Patron.pm (+20 lines)
Lines 264-269 sub store { Link Here
264
                # Make a copy of the plain text password for later use
264
                # Make a copy of the plain text password for later use
265
                $self->plain_text_password( $self->password );
265
                $self->plain_text_password( $self->password );
266
266
267
                $self->password_expiration_date( $self->password
268
                    ? $self->category->get_password_expiry_date
269
                    : undef );
267
                # Create a disabled account if no password provided
270
                # Create a disabled account if no password provided
268
                $self->password( $self->password
271
                $self->password( $self->password
269
                    ? Koha::AuthUtils::hash_password( $self->password )
272
                    ? Koha::AuthUtils::hash_password( $self->password )
Lines 777-782 sub is_expired { Link Here
777
    return 0;
780
    return 0;
778
}
781
}
779
782
783
=head3 password_expired
784
785
my $password_expired = $patron->password_expired;
786
787
Returns 1 if the patron's password is expired or 0;
788
789
=cut
790
791
sub password_expired {
792
    my ($self) = @_;
793
    return 0 unless $self->password_expiration_date;
794
    return 1 if dt_from_string( $self->password_expiration_date ) < dt_from_string->truncate( to => 'day' );
795
    return 0;
796
}
797
780
=head3 is_going_to_expire
798
=head3 is_going_to_expire
781
799
782
my $is_going_to_expire = $patron->is_going_to_expire;
800
my $is_going_to_expire = $patron->is_going_to_expire;
Lines 876-881 sub set_password { Link Here
876
894
877
    my $digest = Koha::AuthUtils::hash_password($password);
895
    my $digest = Koha::AuthUtils::hash_password($password);
878
896
897
    $self->password_expiration_date( $self->category->get_password_expiry_date );
898
879
    # We do not want to call $self->store and retrieve password from DB
899
    # We do not want to call $self->store and retrieve password from DB
880
    $self->password($digest);
900
    $self->password($digest);
881
    $self->login_attempts(0);
901
    $self->login_attempts(0);
(-)a/Koha/Patron/Category.pm (+20 lines)
Lines 113-118 sub get_expiry_date { Link Here
113
    }
113
    }
114
}
114
}
115
115
116
=head3 get_password_expiry_date
117
118
Returns date based on password expiry days set for the category. If the value is not set
119
we return undef, password does not expire
120
121
my $expiry_date = $category->get_password_expiry_date();
122
123
=cut
124
125
sub get_password_expiry_date {
126
    my ($self, $date ) = @_;
127
    if ( $self->password_expiry_days ) {
128
        $date ||= dt_from_string;
129
        $date = dt_from_string( $date ) unless ref $date;
130
        return $date->add( days => $self->password_expiry_days )->ymd;
131
    } else {
132
        return;
133
    }
134
}
135
116
=head3 effective_reset_password
136
=head3 effective_reset_password
117
137
118
Returns if patrons in this category can reset their password. If set in $self->reset_password
138
Returns if patrons in this category can reset their password. If set in $self->reset_password
(-)a/Koha/REST/V1/Auth.pm (-1 / +6 lines)
Lines 490-496 sub _basic_auth { Link Here
490
        Koha::Exceptions::Authorization::Unauthorized->throw( error => 'Invalid password' );
490
        Koha::Exceptions::Authorization::Unauthorized->throw( error => 'Invalid password' );
491
    }
491
    }
492
492
493
    return Koha::Patrons->find({ userid => $user_id });
493
    my $patron = Koha::Patrons->find({ userid => $user_id });
494
    if ( $patron->password_expired ) {
495
        Koha::Exceptions::Authorization::Unauthorized->throw( error => 'Password has expired' );
496
    }
497
498
    return $patron;
494
}
499
}
495
500
496
=head3 _set_userenv
501
=head3 _set_userenv
(-)a/admin/categories.pl (+3 lines)
Lines 63-68 elsif ( $op eq 'add_validate' ) { Link Here
63
    my $description = $input->param('description');
63
    my $description = $input->param('description');
64
    my $enrolmentperiod = $input->param('enrolmentperiod');
64
    my $enrolmentperiod = $input->param('enrolmentperiod');
65
    my $enrolmentperioddate = $input->param('enrolmentperioddate') || undef;
65
    my $enrolmentperioddate = $input->param('enrolmentperioddate') || undef;
66
    my $password_expiry_days = $input->param('password_expiry_days') || undef;
66
    my $upperagelimit = $input->param('upperagelimit');
67
    my $upperagelimit = $input->param('upperagelimit');
67
    my $dateofbirthrequired = $input->param('dateofbirthrequired');
68
    my $dateofbirthrequired = $input->param('dateofbirthrequired');
68
    my $enrolmentfee = $input->param('enrolmentfee');
69
    my $enrolmentfee = $input->param('enrolmentfee');
Lines 103-108 elsif ( $op eq 'add_validate' ) { Link Here
103
        $category->description($description);
104
        $category->description($description);
104
        $category->enrolmentperiod($enrolmentperiod);
105
        $category->enrolmentperiod($enrolmentperiod);
105
        $category->enrolmentperioddate($enrolmentperioddate);
106
        $category->enrolmentperioddate($enrolmentperioddate);
107
        $category->password_expiry_days($password_expiry_days);
106
        $category->upperagelimit($upperagelimit);
108
        $category->upperagelimit($upperagelimit);
107
        $category->dateofbirthrequired($dateofbirthrequired);
109
        $category->dateofbirthrequired($dateofbirthrequired);
108
        $category->enrolmentfee($enrolmentfee);
110
        $category->enrolmentfee($enrolmentfee);
Lines 134-139 elsif ( $op eq 'add_validate' ) { Link Here
134
            description => $description,
136
            description => $description,
135
            enrolmentperiod => $enrolmentperiod,
137
            enrolmentperiod => $enrolmentperiod,
136
            enrolmentperioddate => $enrolmentperioddate,
138
            enrolmentperioddate => $enrolmentperioddate,
139
            password_expiry_days => $password_expiry_days,
137
            upperagelimit => $upperagelimit,
140
            upperagelimit => $upperagelimit,
138
            dateofbirthrequired => $dateofbirthrequired,
141
            dateofbirthrequired => $dateofbirthrequired,
139
            enrolmentfee => $enrolmentfee,
142
            enrolmentfee => $enrolmentfee,
(-)a/koha-tmpl/intranet-tmpl/prog/en/modules/admin/categories.tt (+11 lines)
Lines 162-167 Link Here
162
                        </ol>
162
                        </ol>
163
                    </fieldset>
163
                    </fieldset>
164
                </li>
164
                </li>
165
                <li>
166
                    <label for="password_expiry_days">Password expiration: </label>
167
                    <input type="text" name="password_expiry_days" id="password_expiry_days" value="[% category.password_expiry_days | html %]" size="3" maxlength="5" /> days
168
                </li>
165
                <li>
169
                <li>
166
                    <label for="dateofbirthrequired">Age required: </label>
170
                    <label for="dateofbirthrequired">Age required: </label>
167
                    <input type="text" name="dateofbirthrequired" id="dateofbirthrequired" value="[% category.dateofbirthrequired | html %]" size="3" maxlength="3" /> years
171
                    <input type="text" name="dateofbirthrequired" id="dateofbirthrequired" value="[% category.dateofbirthrequired | html %]" size="3" maxlength="3" /> years
Lines 449-454 Link Here
449
                        [% END %]
453
                        [% END %]
450
                    </td>
454
                    </td>
451
                </tr>
455
                </tr>
456
                <tr><th scope="row">Password expiration: </th><td>[% category.password_expiry_days | html %] days</td></tr>
452
                <tr><th scope="row">Age required: </th><td>[% category.dateofbirthrequired | html %] years</td></tr>
457
                <tr><th scope="row">Age required: </th><td>[% category.dateofbirthrequired | html %] years</td></tr>
453
                <tr><th scope="row">Upperage limit: </th><td>[% category.upperagelimit | html %] years</td></tr>
458
                <tr><th scope="row">Upperage limit: </th><td>[% category.upperagelimit | html %] years</td></tr>
454
                <tr><th scope="row">Enrollment fee: </th><td>[% category.enrolmentfee | $Price %]</td></tr>
459
                <tr><th scope="row">Enrollment fee: </th><td>[% category.enrolmentfee | $Price %]</td></tr>
Lines 517-522 Link Here
517
                    <th scope="col">Category name</th>
522
                    <th scope="col">Category name</th>
518
                    <th scope="col">Type</th>
523
                    <th scope="col">Type</th>
519
                    <th scope="col">Enrollment period</th>
524
                    <th scope="col">Enrollment period</th>
525
                    <th scope="col">Password expiration</th>
520
                    <th scope="col">Age required</th>
526
                    <th scope="col">Age required</th>
521
                    <th scope="col">Upper age limit</th>
527
                    <th scope="col">Upper age limit</th>
522
                    <th scope="col">Enrollment fee</th>
528
                    <th scope="col">Enrollment fee</th>
Lines 559-564 Link Here
559
                                until [% category.enrolmentperioddate | $KohaDates %]
565
                                until [% category.enrolmentperioddate | $KohaDates %]
560
                            [% END %]
566
                            [% END %]
561
                        </td>
567
                        </td>
568
                        [% IF (category.password_expiry_days) %]
569
                            <td>[% category.password_expiry_days | html %] days</td>
570
                        [% ELSE %]
571
                            <td>-</td>
572
                        [% END %]
562
                        [% IF (category.dateofbirthrequired) %]
573
                        [% IF (category.dateofbirthrequired) %]
563
                            <td>[% category.dateofbirthrequired | html %] years</td>
574
                            <td>[% category.dateofbirthrequired | html %] years</td>
564
                        [% ELSE %]
575
                        [% ELSE %]
(-)a/koha-tmpl/intranet-tmpl/prog/en/modules/auth.tt (+7 lines)
Lines 51-56 Link Here
51
    [% END %]
51
    [% END %]
52
[% ELSIF invalid_username_or_password %]
52
[% ELSIF invalid_username_or_password %]
53
<div id="login_error"><strong>Error: </strong>Invalid username or password</div>
53
<div id="login_error"><strong>Error: </strong>Invalid username or password</div>
54
[% ELSIF password_has_expired %]
55
    <div id="login_error"><strong>Error: </strong>Your password has expired!</div>
56
    [% IF Categories.can_any_reset_password && Koha.Preference('OpacBaseURL') %]
57
        <a href="[% Koha.Preference('OpacBaseURL') | url %]/cgi-bin/koha/opac-password-recovery.pl">You must reset your password</a>.
58
    [% ELSE %]
59
        <p>You must contact the library to have your password reset</p>
60
    [% END %]
54
[% END %]
61
[% END %]
55
62
56
[% IF (shibbolethAuthentication) %]
63
[% IF (shibbolethAuthentication) %]
(-)a/koha-tmpl/opac-tmpl/bootstrap/en/modules/opac-auth.tt (-3 / +11 lines)
Lines 167-173 Link Here
167
                            [% END # /IF GoogleOpenIDConnect %]
167
                            [% END # /IF GoogleOpenIDConnect %]
168
                        [% END # /UNLESS OPACShibOnly %]
168
                        [% END # /UNLESS OPACShibOnly %]
169
169
170
                        [% IF !Koha.Preference('OPACShibOnly') or SCO_login or SCI_login %]
170
                        [% IF password_has_expired %]
171
                            <p class="error"><strong>Error: </strong>Your password has expired!</p>
172
                            [% IF Koha.Preference('OpacPasswordChange') && Categories.can_any_reset_password %]
173
                                <div id="resetpassword">
174
                                    <a href="/cgi-bin/koha/opac-password-recovery.pl">Reset your password?</a>
175
                                </div>
176
                            [% ELSE %]
177
                                <p>You must contact the library to reset your password</p>
178
                            [% END %]
179
                        [% ELSIF !Koha.Preference('OPACShibOnly') or SCO_login or SCI_login %]
171
                            [% IF SCO_login %]
180
                            [% IF SCO_login %]
172
                                <form action="/cgi-bin/koha/sco/sco-main.pl" name="auth" id="auth" method="post" autocomplete="off">
181
                                <form action="/cgi-bin/koha/sco/sco-main.pl" name="auth" id="auth" method="post" autocomplete="off">
173
                            [% ELSIF SCI_login %]
182
                            [% ELSIF SCI_login %]
Lines 217-223 Link Here
217
                                    [% END %]
226
                                    [% END %]
218
                                </div>
227
                                </div>
219
                            </form>
228
                            </form>
220
                        [% END # / IF !OPACShibOnly or SCO_login or SCI_login %]
229
                        [% END # / IF password_has_expired / ELSIF !OPACShibOnly or SCO_login or SCI_login %]
221
                    [% END # / IF loginprompt %]
230
                    [% END # / IF loginprompt %]
222
231
223
                    [% ELSE %]
232
                    [% ELSE %]
224
- 

Return to bug 29924