Bivio::Biz::Model::User
# Copyright (c) 1999-2010 bivio Software, Inc. All rights reserved. # $Id$ package Bivio::Biz::Model::User; use strict; use Bivio::Base 'Model.RealmOwnerBase'; my($_ADMINISTRATOR) = __PACKAGE__->use('Auth.Role')->ADMINISTRATOR; sub concat_last_first_middle { my(undef, $last, $first, $middle) = @_; if (defined($last)) { my($res) = undef; return $last unless defined($first) || defined($middle); $res = $last . ','; $res .= ' ' . $first if defined($first); $res .= ' ' . $middle if defined($middle); return $res; } return $first . ' ' . $middle if defined($first) && defined($middle); return defined($first) ? $first : $middle; } sub create { my($self, $values) = @_; # Sets I<gender> if not set and computes the sorting name fields then # calls SUPER. $values->{gender} ||= $self->get_field_type('gender')->UNKNOWN; _compute_sorting_names($values); my($res) = $self->SUPER::create($values); _validate_names($self); return $res; } sub create_realm { my($self, $user, $realm_owner) = (shift, shift, shift); return $self->create($user)->SUPER::create_realm({ %$realm_owner, defined($realm_owner->{password}) ? (password => $self->use('Type.Password')->encrypt( $realm_owner->{password})) : (), display_name => $self->format_full_name, }, @_); } sub format_full_name { my($proto, $model, $model_prefix) = shift->internal_get_target(@_); # Returns the first, middle, and last names as one string. # # B<You should use RealmOwner.display_name whenever possible as the # values are identical.> my($res) = ''; foreach my $name ($model->unsafe_get($model_prefix.'first_name', $model_prefix . 'middle_name', $model_prefix . 'last_name')) { $res .= $name . ' ' if defined($name) && length($name); } # Get rid of last ' ' chop($res); return $res; } sub format_last_first_middle { my($proto, $model, $model_prefix) = shift->internal_get_target(@_); # Return Last, First Middle. # # See L<format_name|"format_name"> for params. return $proto->concat_last_first_middle($model->unsafe_get( $model_prefix . 'last_name', $model_prefix . 'first_name', $model_prefix . 'middle_name')); } sub get_outgoing_emails { my($self, $which) = @_; # Returns an array of outgoing addresses for this user if no # I<which>. Otherwise, returns a single address. # # Returns C<undef> is there are no outgoing email addresses for # this user. my($email) = $self->new_other('Email'); return undef unless $email->unauth_load({ location => $which || $email->get_field_type('location')->HOME, realm_id => $self->get('user_id'), }); # Validate address return undef unless $email->get_field_type('email')->is_valid($email->get('email')); return [$email->get('email')]; } sub internal_create_realm_administrator_id { return shift->get('user_id'); } sub internal_initialize { return { version => 1, table_name => 'user_t', columns => { user_id => ['RealmOwner.realm_id', 'PRIMARY_KEY'], first_name => ['Name', 'NONE'], first_name_sort => ['Name', 'NONE'], middle_name => ['Name', 'NONE'], middle_name_sort => ['Name', 'NONE'], last_name => ['Name', 'NONE'], last_name_sort => ['Name', 'NONE'], gender => ['Gender', 'NOT_NULL'], birth_date => ['Date', 'NONE'], }, other => [ [qw(user_id RealmOwner.realm_id)], ], auth_id => 'user_id', }; } sub invalidate_email { my($self) = @_; # Invalidates user's e-mail address be prefixing it with "invalid:". # Checks to see if already invalidated. $self->new_other('Email')->unauth_load_or_die({ realm_id => $self->get('user_id'), })->invalidate; return; } sub set_encrypted_password { my($self, $encrypted) = @_; # Sets a user's encrypted password to a new value. return _get_realm->update({password => $encrypted}); } sub unauth_delete_realm { my($self, $realm_owner) = @_; my($rid) = $realm_owner->get('realm_id'); $self->new_other('RealmUser')->unauth_delete({ realm_id => $rid, user_id => $rid, role => $_ADMINISTRATOR, }); return shift->SUPER::unauth_delete_realm(@_); } sub update { my($self, $new_values) = @_; # Updates the current model's values. Validates one of # first, last and middle are set. _compute_sorting_names($new_values); my($res) = $self->SUPER::update($new_values); _validate_names($self); $self->get_model('RealmOwner')->update({ display_name => $self->format_full_name, }); return $res; } sub _compute_sorting_names { my($values) = @_; foreach my $field (qw(first_name middle_name last_name)) { my($sort) = $field . '_sort'; unless (exists($values->{$field})) { delete($values->{$sort}); next; } if (defined($values->{$field}) && length($values->{$field})) { $values->{$sort} = lc($values->{$field}); } else { $values->{$field} = undef; $values->{$sort} = undef; } } return; } sub _get_realm { my($self) = @_; # Returns the realm owner for the current user_id. return $self->new_other('RealmOwner')->unauth_load_or_die({ realm_id => $self->get('user_id'), }); } sub _validate_names { my($self) = @_; # Dies unless at least one of first/middle/last names are set. $self->die('must have at least one of first, last, and middle names') unless defined($self->get('first_name')) || defined($self->get('middle_name')) || defined($self->get('last_name')); return; } 1;