From 421ff7f194875db9634ea783d9dd5b6111f19df3 Mon Sep 17 00:00:00 2001 From: Byron Jones Date: Tue, 1 Sep 2015 13:01:20 +0800 Subject: Bug 1197073 - add support for 2fa using totp (eg. google authenticator) --- Bugzilla/User.pm | 38 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 38 insertions(+) (limited to 'Bugzilla/User.pm') diff --git a/Bugzilla/User.pm b/Bugzilla/User.pm index 4a0c2166d..d3bb807b3 100644 --- a/Bugzilla/User.pm +++ b/Bugzilla/User.pm @@ -108,6 +108,7 @@ sub DB_COLUMNS { $dbh->sql_date_format('last_seen_date', '%Y-%m-%d') . ' AS last_seen_date', 'profiles.password_change_required', 'profiles.password_change_reason', + 'profiles.mfa', ), } @@ -125,6 +126,7 @@ use constant VALIDATORS => { is_enabled => \&_check_is_enabled, password_change_required => \&Bugzilla::Object::check_boolean, password_change_reason => \&_check_password_change_reason, + mfa => \&_check_mfa, }; sub UPDATE_COLUMNS { @@ -138,6 +140,7 @@ sub UPDATE_COLUMNS { is_enabled password_change_required password_change_reason + mfa ); push(@cols, 'cryptpassword') if exists $self->{cryptpassword}; return @cols; @@ -266,6 +269,10 @@ sub update { $self->derive_regexp_groups(); } + if (exists $changes->{mfa} && $self->mfa eq '') { + $dbh->do("DELETE FROM profile_mfa WHERE user_id = ?", undef, $self->id); + } + # Logout the user if necessary. Bugzilla->logout_user($self) if (!$options->{keep_session} @@ -357,6 +364,13 @@ sub _check_password_change_reason { : ''; } +sub _check_mfa { + my ($self, $provider) = @_; + $provider = lc($provider // ''); + return 'TOTP' if $provider eq 'totp'; + return ''; +} + ################################################################################ # Mutators ################################################################################ @@ -394,6 +408,15 @@ sub set_disabledtext { $self->set('disable_mail', 1) if !$self->is_enabled; } +sub set_mfa { + my ($self, $value) = @_; + if ($value eq '' && $self->mfa) { + $self->mfa_provider->property_delete_all(); + } + $self->set('mfa', $value); + delete $self->{mfa_provider}; +} + sub set_groups { my $self = shift; $self->_set_groups(GROUP_MEMBERSHIP, @_); @@ -561,6 +584,21 @@ sub authorizer { return $self->{authorizer}; } +sub mfa { $_[0]->{mfa} } +sub mfa_provider { + my ($self) = @_; + my $mfa = $self->{mfa} || return undef; + return $self->{mfa_provider} if exists $self->{mfa_provider}; + if ($mfa eq 'TOTP') { + require Bugzilla::MFA::TOTP; + $self->{mfa_provider} = Bugzilla::MFA::TOTP->new($self); + } + else { + $self->{mfa_provider} = undef; + } + return $self->{mfa_provider}; +} + # Generate a string to identify the user by name + login if the user # has a name or by login only if she doesn't. sub identity { -- cgit v1.2.3-24-g4f1b