Subversion Repositories oidplus

Rev

Rev 300 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
104 daniel-mar 1
<?php
2
 
3
/*
4
 * OIDplus 2.0
5
 * Copyright 2019 Daniel Marschall, ViaThinkSoft
6
 *
7
 * Licensed under the Apache License, Version 2.0 (the "License");
8
 * you may not use this file except in compliance with the License.
9
 * You may obtain a copy of the License at
10
 *
11
 *     http://www.apache.org/licenses/LICENSE-2.0
12
 *
13
 * Unless required by applicable law or agreed to in writing, software
14
 * distributed under the License is distributed on an "AS IS" BASIS,
15
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16
 * See the License for the specific language governing permissions and
17
 * limitations under the License.
18
 */
19
 
256 daniel-mar 20
class OIDplusPagePublicLogin extends OIDplusPagePluginPublic {
104 daniel-mar 21
 
321 daniel-mar 22
        public function action($actionID, $params) {
104 daniel-mar 23
                // === RA LOGIN/LOGOUT ===
24
 
321 daniel-mar 25
                if ($actionID == 'ra_login') {
26
                        $email = $params['email'];
119 daniel-mar 27
                        $ra = new OIDplusRA($email);
148 daniel-mar 28
 
261 daniel-mar 29
                        if (OIDplus::baseConfig()->getValue('RECAPTCHA_ENABLED', false)) {
30
                                $secret=OIDplus::baseConfig()->getValue('RECAPTCHA_PRIVATE', '');
321 daniel-mar 31
                                $response=$params["captcha"];
104 daniel-mar 32
                                $verify=file_get_contents("https://www.google.com/recaptcha/api/siteverify?secret={$secret}&response={$response}");
33
                                $captcha_success=json_decode($verify);
34
                                if ($captcha_success->success==false) {
250 daniel-mar 35
                                        throw new OIDplusException('Captcha wrong');
104 daniel-mar 36
                                }
37
                        }
38
 
321 daniel-mar 39
                        if ($ra->checkPassword($params['password'])) {
288 daniel-mar 40
                                OIDplus::logger()->log("[OK]RA($email)!", "RA '$email' logged in");
119 daniel-mar 41
                                OIDplus::authUtils()::raLogin($email);
104 daniel-mar 42
 
264 daniel-mar 43
                                OIDplus::db()->query("UPDATE ###ra set last_login = ".OIDplus::db()->sqlDate()." where email = ?", array($email));
104 daniel-mar 44
 
107 daniel-mar 45
                                echo json_encode(array("status" => 0));
104 daniel-mar 46
                        } else {
300 daniel-mar 47
                                if (OIDplus::config()->getValue('log_failed_ra_logins', false)) {
298 daniel-mar 48
                                        if ($ra->existing()) {
49
                                                OIDplus::logger()->log("[WARN]A!", "Failed login to RA account '$email' (wrong password)");
50
                                        } else {
51
                                                OIDplus::logger()->log("[WARN]A!", "Failed login to RA account '$email' (RA not existing)");
52
                                        }
295 daniel-mar 53
                                }
251 daniel-mar 54
                                throw new OIDplusException('Wrong password or user not registered');
104 daniel-mar 55
                        }
150 daniel-mar 56
 
321 daniel-mar 57
                } else if ($actionID == 'ra_logout') {
119 daniel-mar 58
 
321 daniel-mar 59
                        $email = $params['email'];
60
 
288 daniel-mar 61
                        OIDplus::logger()->log("[OK]RA($email)!", "RA '$email' logged out");
119 daniel-mar 62
                        OIDplus::authUtils()::raLogout($email);
107 daniel-mar 63
                        echo json_encode(array("status" => 0));
104 daniel-mar 64
                }
65
 
66
                // === ADMIN LOGIN/LOGOUT ===
67
 
321 daniel-mar 68
                else if ($actionID == 'admin_login') {
261 daniel-mar 69
                        if (OIDplus::baseConfig()->getValue('RECAPTCHA_ENABLED', false)) {
70
                                $secret=OIDplus::baseConfig()->getValue('RECAPTCHA_PRIVATE', '');
321 daniel-mar 71
                                $response=$params["captcha"];
104 daniel-mar 72
                                $verify=file_get_contents("https://www.google.com/recaptcha/api/siteverify?secret={$secret}&response={$response}");
73
                                $captcha_success=json_decode($verify);
74
                                if ($captcha_success->success==false) {
250 daniel-mar 75
                                        throw new OIDplusException('Captcha wrong');
104 daniel-mar 76
                                }
77
                        }
78
 
321 daniel-mar 79
                        if (OIDplus::authUtils()::adminCheckPassword($params['password'])) {
288 daniel-mar 80
                                OIDplus::logger()->log("[OK]A!", "Admin logged in");
104 daniel-mar 81
                                OIDplus::authUtils()::adminLogin();
107 daniel-mar 82
                                echo json_encode(array("status" => 0));
104 daniel-mar 83
                        } else {
300 daniel-mar 84
                                if (OIDplus::config()->getValue('log_failed_admin_logins', false)) {
298 daniel-mar 85
                                        OIDplus::logger()->log("[WARN]A!", "Failed login to admin account");
86
                                }
250 daniel-mar 87
                                throw new OIDplusException('Wrong password');
104 daniel-mar 88
                        }
89
                }
321 daniel-mar 90
                else if ($actionID == 'admin_logout') {
288 daniel-mar 91
                        OIDplus::logger()->log("[OK]A!", "Admin logged out");
104 daniel-mar 92
                        OIDplus::authUtils()::adminLogout();
107 daniel-mar 93
                        echo json_encode(array("status" => 0));
104 daniel-mar 94
                }
321 daniel-mar 95
                else {
96
                        throw new OIDplusException("Unknown action ID");
97
                }
104 daniel-mar 98
        }
99
 
100
        public function init($html=true) {
295 daniel-mar 101
                OIDplus::config()->prepareConfigKey('log_failed_ra_logins', 'Log failed RA logins', '0', OIDplusConfig::PROTECTION_EDITABLE, function($value) {
102
                        if (!is_numeric($value) || (($value != 0) && (($value != 1)))) {
103
                                throw new OIDplusException("Valid values: 0 (off) or 1 (on).");
104
                        }
105
                });
106
                OIDplus::config()->prepareConfigKey('log_failed_admin_logins', 'Log failed Admin logins', '0', OIDplusConfig::PROTECTION_EDITABLE, function($value) {
107
                        if (!is_numeric($value) || (($value != 0) && (($value != 1)))) {
108
                                throw new OIDplusException("Valid values: 0 (off) or 1 (on).");
109
                        }
110
                });
104 daniel-mar 111
        }
112
 
113
        public function gui($id, &$out, &$handled) {
114
                if ($id === 'oidplus:login') {
115
                        $handled = true;
116
                        $out['title'] = 'Login';
241 daniel-mar 117
                        $out['icon']  = OIDplus::webpath(__DIR__).'login_big.png';
104 daniel-mar 118
 
119
                        $out['text'] .= '<noscript>';
120
                        $out['text'] .= '<p>You need to enable JavaScript to use the login area.</p>';
121
                        $out['text'] .= '</noscript>';
122
 
219 daniel-mar 123
                        $out['text'] .= '<div id="loginArea" style="visibility: hidden"><div id="loginTab" class="container" style="width:100%;">';
261 daniel-mar 124
                        $out['text'] .= (OIDplus::baseConfig()->getValue('RECAPTCHA_ENABLED', false) ?
125
                                        '<script> grecaptcha.render(document.getElementById("g-recaptcha"), { "sitekey" : "'.OIDplus::baseConfig()->getValue('RECAPTCHA_PUBLIC', '').'" }); </script>'.
126
                                        '<p>Before logging in, please solve the following CAPTCHA</p><div id="g-recaptcha" class="g-recaptcha" data-sitekey="'.OIDplus::baseConfig()->getValue('RECAPTCHA_PUBLIC', '').'"></div>' : '');
104 daniel-mar 127
                        $out['text'] .= '<br>';
219 daniel-mar 128
                        $out['text'] .= '<ul class="nav nav-pills">';
104 daniel-mar 129
                        $out['text'] .= '                       <li class="active">';
119 daniel-mar 130
                        $out['text'] .= '                       <a href="#1a" data-toggle="tab">Login as RA</a>';
104 daniel-mar 131
                        $out['text'] .= '                       </li>';
132
                        $out['text'] .= '                       <li><a href="#2a" data-toggle="tab">Login as administrator</a>';
133
                        $out['text'] .= '                       </li>';
134
                        $out['text'] .= '               </ul>';
135
                        $out['text'] .= '                       <div class="tab-content clearfix">';
136
                        $out['text'] .= '                         <div class="tab-pane active" id="1a">';
137
 
138
                        $out['text'] .= '<h2>Login as RA</h2>';
139
 
140
                        $login_list = OIDplus::authUtils()->loggedInRaList();
141
                        if (count($login_list) > 0) {
115 daniel-mar 142
                                foreach ($login_list as $x) {
143
                                        $out['text'] .= '<p>You are logged in as <b>'.$x->raEmail().'</b> (<a href="#" onclick="return raLogout('.js_escape($x->raEmail()).');">Logout</a>)</p>';
104 daniel-mar 144
                                }
145
                                $out['text'] .= '<p>If you have more accounts, you can log in with a new account:</p>';
146
                        } else {
147
                                $out['text'] .= '<p>Enter your email address and your password to log in as Registration Authority.</p>';
148
                        }
107 daniel-mar 149
                        $out['text'] .= '<form onsubmit="return raLoginOnSubmit(this);">';
104 daniel-mar 150
                        $out['text'] .= '<input type="hidden" name="action" value="ra_login">';
152 daniel-mar 151
                        $out['text'] .= '<div><label class="padding_label">E-Mail:</label><input type="text" name="email" value="" id="raLoginEMail"></div>';
152
                        $out['text'] .= '<div><label class="padding_label">Password:</label><input type="password" name="password" value="" id="raLoginPassword"></div>';
153
                        $out['text'] .= '<br><input type="submit" value="Login"><br><br>';
104 daniel-mar 154
                        $out['text'] .= '</form>';
250 daniel-mar 155
                        $out['text'] .= '<p><a '.OIDplus::gui()->link('oidplus:forgot_password').'>Forgot password?</a><br>';
104 daniel-mar 156
 
256 daniel-mar 157
                        if (class_exists('OIDplusPageRaInvite') && OIDplus::config()->getValue('ra_invitation_enabled')) {
156 daniel-mar 158
                                $out['text'] .= '<abbr title="To receive login data, the superior RA needs to send you an invitation. After creating or updating your OID, the system will ask them if they want to send you an invitation. If they accept, you will receive an email with an activation link. Alternatively, the system admin can create your account manually in the administrator control panel.">How to register?</abbr></p>';
159
                        } else {
160
                                $out['text'] .= '<abbr title="Since invitations are disabled at this OIDplus installation, the system administrator needs to create your account manually in the administrator control panel.">How to register?</abbr></p>';
161
                        }
162
 
104 daniel-mar 163
                        $out['text'] .= '                               </div>';
164
                        $out['text'] .= '                               <div class="tab-pane" id="2a">';
165
 
166
                        if (OIDplus::authUtils()::isAdminLoggedIn()) {
167
                                $out['text'] .= '<h2>Admin login</h2>';
168
                                $out['text'] .= '<p>You are logged in as administrator.</p>';
169
                                $out['text'] .= '<a href="#" onclick="return adminLogout();">Logout</a>';
170
                        } else {
171
                                $out['text'] .= '<h2>Login as administrator</h2>';
107 daniel-mar 172
                                $out['text'] .= '<form onsubmit="return adminLoginOnSubmit(this);">';
104 daniel-mar 173
                                $out['text'] .= '<input type="hidden" name="action" value="admin_login">';
152 daniel-mar 174
                                $out['text'] .= '<div><label class="padding_label">Password:</label><input type="password" name="password" value="" id="adminLoginPassword"></div>';
175
                                $out['text'] .= '<br><input type="submit" value="Login"><br><br>';
104 daniel-mar 176
                                $out['text'] .= '</form>';
250 daniel-mar 177
                                $out['text'] .= '<p><a '.OIDplus::gui()->link('oidplus:forgot_password_admin').'>Forgot password?</a><br>';
104 daniel-mar 178
                        }
179
 
180
                        $out['text'] .= '                               </div>';
181
                        $out['text'] .= '                       </div>';
182
                        $out['text'] .= '  </div><br>';
183
                        $out['text'] .= '<p><font size="-1"><i>Privacy information</i>: By using the login functionality, you are accepting that a "session cookie" is temporarily stored in your browser. '.
184
                                        'The session cookie is a small text file that is sent to this website every time you visit it, to identify you as an already logged in user. '.
261 daniel-mar 185
                                        'It does not track any of your online activities outside OIDplus. The cookie will be destroyed when you log out or after an inactivity of '.ceil(OIDplus::baseConfig()->getValue('SESSION_LIFETIME', 30*60)/60).' minutes.';
296 daniel-mar 186
                        $privacy_document_file = 'OIDplus/privacy_documentation.html';
187
                        if (class_exists('OIDplusPagePublicResources') && file_exists(OIDplus::basePath().'/res/'.$privacy_document_file)) {
250 daniel-mar 188
                                $out['text'] .= ' <a '.OIDplus::gui()->link('oidplus:resources$'.$privacy_document_file.'$'.OIDplus::authUtils()::makeAuthKey("resources;".$privacy_document_file).'#cookies').'>More information about the cookies used</a>';
219 daniel-mar 189
                        }
190
                        $out['text'] .= '</font></p></div>';
107 daniel-mar 191
 
192
                        $out['text'] .= '<script>document.getElementById("loginArea").style.visibility = "visible";</script>';
104 daniel-mar 193
                }
194
        }
295 daniel-mar 195
 
282 daniel-mar 196
        public function publicSitemap(&$out) {
283 daniel-mar 197
                $out[] = OIDplus::getSystemUrl().'?goto='.urlencode('oidplus:login');
282 daniel-mar 198
        }
104 daniel-mar 199
 
106 daniel-mar 200
        public function tree(&$json, $ra_email=null, $nonjs=false, $req_goto='') {
104 daniel-mar 201
                $loginChildren = array();
202
 
203
                if (OIDplus::authUtils()::isAdminLoggedIn()) {
204
                        $ra_roots = array();
205
 
281 daniel-mar 206
                        foreach (OIDplus::getPagePlugins() as $plugin) {
207
                                if (is_subclass_of($plugin, OIDplusPagePluginAdmin::class)) {
208
                                        $plugin->tree($ra_roots);
209
                                }
104 daniel-mar 210
                        }
211
 
212
                        $ra_roots[] = array(
213
                                'id'       => 'oidplus:logout$admin',
241 daniel-mar 214
                                'icon'     => OIDplus::webpath(__DIR__).'treeicon_logout.png',
225 daniel-mar 215
                                'conditionalselect' => 'adminLogout()', // defined in oidplus_base.js
104 daniel-mar 216
                                'text'     => 'Log out'
217
                        );
218
                        $loginChildren[] = array(
219
                                'id'       => 'oidplus:dummy$'.md5(rand()),
220
                                'text'     => "Logged in as admin",
241 daniel-mar 221
                                'icon'     => OIDplus::webpath(__DIR__).'treeicon_admin.png',
104 daniel-mar 222
                                'conditionalselect' => 'false', // dummy node that can't be selected
223
                                'state'    => array("opened" => true),
224
                                'children' => $ra_roots
225
                        );
226
                }
227
 
115 daniel-mar 228
                foreach (OIDplus::authUtils()::loggedInRaList() as $ra) {
229
                        $ra_email = $ra->raEmail();
104 daniel-mar 230
                        $ra_roots = array();
231
 
281 daniel-mar 232
                        foreach (OIDplus::getPagePlugins() as $plugin) {
233
                                if (is_subclass_of($plugin, OIDplusPagePluginRa::class)) {
234
                                        $plugin->tree($ra_roots, $ra_email);
235
                                }
104 daniel-mar 236
                        }
237
 
238
                        $ra_roots[] = array(
239
                                'id'       => 'oidplus:logout$'.$ra_email,
225 daniel-mar 240
                                'conditionalselect' => 'raLogout('.js_escape($ra_email).')', // defined in oidplus_base.js
241 daniel-mar 241
                                'icon'     => OIDplus::webpath(__DIR__).'treeicon_logout.png',
104 daniel-mar 242
                                'text'     => 'Log out'
243
                        );
244
                        foreach (OIDplusObject::getRaRoots($ra_email) as $loc_root) {
245
                                $ico = $loc_root->getIcon();
246
                                $ra_roots[] = array(
247
                                        'id' => 'oidplus:raroot$'.$loc_root->nodeId(),
248
                                        'text' => 'Jump to RA root '.$loc_root->objectTypeTitleShort().' '.$loc_root->crudShowId(OIDplusObject::parse($loc_root::root())),
110 daniel-mar 249
                                        'conditionalselect' => 'openOidInPanel('.js_escape($loc_root->nodeId()).', true);',
241 daniel-mar 250
                                        'icon' => !is_null($ico) ? $ico : OIDplus::webpath(__DIR__).'treeicon_link.png'
104 daniel-mar 251
                                );
252
                        }
253
                        $ra_email_or_name = (new OIDplusRA($ra_email))->raName();
254
                        if ($ra_email_or_name == '') $ra_email_or_name = $ra_email;
255
                        $loginChildren[] = array(
256
                                'id'       => 'oidplus:dummy$'.md5(rand()),
257
                                'text'     => "Logged in as ".htmlentities($ra_email_or_name),
241 daniel-mar 258
                                'icon'     => OIDplus::webpath(__DIR__).'treeicon_ra.png',
104 daniel-mar 259
                                'conditionalselect' => 'false', // dummy node that can't be selected
260
                                'state'    => array("opened" => true),
261
                                'children' => $ra_roots
262
                        );
263
                }
264
 
265
                $json[] = array(
266
                        'id'       => 'oidplus:login',
241 daniel-mar 267
                        'icon'     => OIDplus::webpath(__DIR__).'treeicon_login.png',
104 daniel-mar 268
                        'text'     => 'Login',
269
                        'state'    => array("opened" => count($loginChildren)>0),
270
                        'children' => $loginChildren
271
                );
272
 
273
                return true;
274
        }
108 daniel-mar 275
 
276
        public function tree_search($request) {
277
                return false;
278
        }
104 daniel-mar 279
}