$::form->read_version auf SL::Version->get_version umgestellt
[kivitendo-erp.git] / SL / Controller / LoginScreen.pm
1 package SL::Controller::LoginScreen;
2
3 use strict;
4
5 use parent qw(SL::Controller::Base);
6
7 use List::Util qw(first);
8
9 use SL::Dispatcher::AuthHandler::User;
10 use SL::DB::AuthClient;
11 use SL::DB::AuthGroup;
12 use SL::DB::AuthUser;
13 use SL::DB::Employee;
14 use SL::Locale::String qw(t8);
15 use SL::User;
16 use SL::Version;
17
18 use Rose::Object::MakeMethods::Generic (
19   'scalar --get_set_init' => [ qw(clients default_client_id) ],
20 );
21
22 __PACKAGE__->run_before('set_layout');
23
24 #
25 # actions
26 #
27
28 sub action_user_login {
29   my ($self) = @_;
30
31   # If the user is already logged in then redirect to the proper menu
32   # script.
33   return if $self->_redirect_to_main_script_if_already_logged_in;
34
35   # Otherwise show the login form.
36   $self->show_login_form(error_state($::form->{error}));
37 }
38
39 sub action_logout {
40   my ($self) = @_;
41
42   $::auth->destroy_session;
43   $::auth->create_or_refresh_session;
44   $self->show_login_form(info => $::locale->text('You are logged out!'));
45 }
46
47 sub action_login {
48   my ($self) = @_;
49
50   my $login     = $::form->{'{AUTH}login'}     || $::auth->get_session_value('login');
51   my $client_id = $::form->{'{AUTH}client_id'} || $::auth->get_session_value('client_id');
52   my $error     = t8('Incorrect username or password or no access to selected client!');
53
54   if (!$::auth->set_client($client_id)) {
55     $::auth->punish_wrong_login;
56     return $self->show_login_form(error => $error);
57   }
58
59   %::myconfig      = $login ? $::auth->read_user(login => $login) : ();
60   $::locale        = Locale->new($::myconfig{countrycode}) if $::myconfig{countrycode};
61   SL::Dispatcher::AuthHandler::User->new->handle(countrycode => $::myconfig{countrycode});
62
63   $::request->layout(SL::Layout::Dispatcher->new(style => $::myconfig{menustyle}));
64
65   # if we get an error back, bale out
66   my $result = User->new(login => $::myconfig{login})->login($::form);
67
68   # Auth DB needs update? If so log the user out forcefully.
69   if (User::LOGIN_AUTH_DBUPDATE_AVAILABLE() == $result) {
70     $::auth->destroy_session;
71     # must be without layout because menu rights might not exist yet
72     return $self->render('login_screen/auth_db_needs_update', { layout => 0 });
73   }
74
75   # Basic client tables available? If not tell the user to create them
76   # and log the user out forcefully.
77   if (User::LOGIN_BASIC_TABLES_MISSING() == $result) {
78     $::auth->destroy_session;
79     return $self->render('login_screen/basic_tables_missing');
80   }
81
82   # Database update available?
83   $::dispatcher->end_request if User::LOGIN_DBUPDATE_AVAILABLE() == $result;
84
85   # Other login errors.
86   if (User::LOGIN_OK() != $result) {
87     $::auth->punish_wrong_login;
88     return $self->show_login_form(error => $error);
89   }
90
91   # Everything is fine.
92   $::auth->set_cookie_environment_variable();
93
94   $self->_redirect_to_main_script;
95 }
96
97 #
98 # settings
99 #
100 sub get_auth_level {
101   return 'none';
102 }
103
104 sub keep_auth_vars_in_form {
105   return 1;
106 }
107
108 #
109 # private methods
110 #
111
112 sub _redirect_to_main_script {
113   my ($self) = @_;
114
115   return $self->redirect_to($::form->{callback}) if $::form->{callback};
116
117   $self->redirect_to(controller => "login.pl", action => 'company_logo');
118 }
119
120 sub _redirect_to_main_script_if_already_logged_in {
121   my ($self) = @_;
122
123   # Get 'login' from valid session.
124   my $login = $::auth->get_session_value('login');
125   return unless $login;
126
127   # See whether or not the user exists in the database.
128   my %user = $::auth->read_user(login => $login);
129   return if ($user{login} || '') ne $login;
130
131   # Check if there's a client set in the session -- and whether or not
132   # the user still has access to the client.
133   my $client_id = $::auth->get_session_value('client_id');
134   return if !$client_id;
135
136   if (!$::auth->set_client($client_id)) {
137     $::auth->punish_wrong_login;
138     $::auth->destroy_session;
139     $::auth->create_or_refresh_session;
140     $self->show_login_form(error => t8('Incorrect username or password or no access to selected client!'));
141     return 1;
142   }
143
144   # Check if the session is logged in correctly.
145   return if SL::Auth::OK() != $::auth->authenticate($login, undef);
146
147   $::auth->create_or_refresh_session;
148   $::auth->delete_session_value('FLASH');
149
150   $self->_redirect_to_main_script(\%user);
151
152   return 1;
153 }
154
155 sub error_state {
156   my %states = (
157     session  => { warning => t8('The session has expired. Please log in again.')                   },
158     password => { error   => t8('Incorrect username or password or no access to selected client!') },
159     action   => { warning => t8('The action is missing or invalid.')                               },
160   );
161
162   return %{ $states{$_[0]} || {} };
163 }
164
165 sub set_layout {
166   $::request->{layout} = SL::Layout::Dispatcher->new(style => 'login');
167 }
168
169 sub init_clients {
170   return SL::DB::Manager::AuthClient->get_all_sorted;
171 }
172
173 sub init_default_client_id {
174   my ($self)         = @_;
175   my $default_client = first { $_->is_default } @{ $self->clients };
176   return $default_client ? $default_client->id : undef;
177 }
178
179 sub show_login_form {
180   my ($self, %params) = @_;
181
182   $self->render('login_screen/user_login', %params, version => SL::Version->get_version, logo_url => $::form->read_logo );
183 }
184
185 1;