upload facility now works in single CIS mode; some simple command-line video moderati...
[living-lab-site.git] / application / controllers / user.php
1 <?php
2
3 /**
4  * Class User controls video hierarchy and searching
5  *
6  * @category    Controller
7  * @author              Călin-Andrei Burloiu
8  */
9 class User extends CI_Controller {
10
11         private $import = FALSE;
12         private $activated_account = TRUE;
13         private $user_id = NULL;
14
15         public function __construct()
16         {
17                 parent::__construct();
18
19                 $this->lang->load('user');
20                 $this->load->model('users_model');
21         }
22
23         public function index()
24         {
25         }
26         
27         public function test($user_id = 1)
28         {
29 //              echo extension_loaded('gd') ? 'gd' : 'nu';
30         }
31         
32         // DEBUG
33         public function show_session()
34         {
35                 if (ENVIRONMENT == 'production')
36                         die();
37                         
38                 var_dump($this->session->all_userdata());
39         }
40         // DEBUG
41         public function destroy_session()
42         {
43                 if (ENVIRONMENT == 'production')
44                         die();
45                         
46                 $this->session->sess_destroy();
47         }
48         
49         public function ajax_get_captcha()
50         {
51                 $this->load->library('captcha');
52                 $captcha = $this->captcha->get_captcha();
53                 echo $captcha['image'];
54         }
55
56         /**
57         * Login a user and then redirect it to the last page which must be encoded
58         * in $redirect.
59         *
60         * @param string $redirect       contains the last page URI segments encoded
61         * with helper url_encode_segments.
62         */
63         public function login($redirect = '')
64         {
65                 $this->load->library('form_validation');
66                 $this->form_validation->set_error_delimiters('<span class="error">',
67                         '</span>');
68                 
69                 // Normal or OpenID login?
70                 if ($this->input->post('openid') !== FALSE)
71                         $b_openid = TRUE;
72                 else
73                         $b_openid = FALSE;
74                 // Validate the correct form.
75                 $res_form_validation = FALSE;
76                 if (!$b_openid)
77                         $res_form_validation = $this->form_validation->run('login');
78                 else
79                         $res_form_validation = $this->form_validation->run('login_openid');
80
81                 if ($res_form_validation === FALSE)
82                 {
83                         $params = array(        'title' =>
84                                                                         $this->lang->line('ui_nav_menu_login')
85                                                                                 .' &ndash; '
86                                                                                 . $this->config->item('site_name'),
87                                                                 //'metas' => array('description'=>'')
88                         );
89                         $this->load->library('html_head_params', $params);
90                                 
91                         // **
92                         // ** LOADING VIEWS
93                         // **
94                         $this->load->view('html_begin', $this->html_head_params);
95                         $this->load->view('header', array('selected_menu' => 'login'));
96
97                         $main_params['content'] = $this->load->view('user/login_view',
98                                 array('redirect'=> $redirect), TRUE);
99                         $main_params['side'] = $this->load->view('side_default', NULL, TRUE);
100                         $this->load->view('main', $main_params);
101                                 
102                         $this->load->view('footer');
103                         $this->load->view('html_end');
104                 }
105                 else
106                 {
107                         if ($b_openid)
108                         {
109                                 $this->users_model->openid_begin_login(
110                                                 $this->input->post('openid'));
111                                 return;
112                         }
113                         
114                         // Without OpenID
115                         if (! $this->activated_account)
116                                 header('Location: '
117                                         . site_url("user/activate/{$this->user_id}"));
118                         else if (! $this->import)
119                         {
120                                 // Redirect to last page before login. 
121                                 header('Location: '. site_url(urldecode_segments($redirect)));
122                         }
123                         else
124                         {
125                                 // Redirect to account page because an user authenticates here
126                                 // for the first time with external authentication. The page
127                                 // will display imported data.
128                                 header('Location: '. site_url('user/account'));
129                         }
130                 }
131         }
132         
133         public function check_openid_login()
134         {
135                 $user = $this->users_model->openid_complete_login();
136                 
137                 // Authentication failed.
138                 if ($user == Auth_OpenID_CANCEL)
139                 {
140                         $this->load->helper('message');
141                         show_error_msg_page($this, $this->lang->line('openid_cancel'));
142                         return;
143                 }               
144                 else if ($user == Auth_OpenID_FAILURE)
145                 {
146                         $this->load->helper('message');
147                         show_error_msg_page($this, $this->lang->line('openid_failure'));
148                         return;
149                 }
150
151                 // Authentication successful: set session with user data.
152                 $this->session->set_userdata(array(
153                         'user_id'=> $user['id'],
154                         'username'=> $user['username'],
155                         'auth_src'=> $user['auth_src'],
156                         'time_zone'=> $user['time_zone']
157                 ));
158                 
159                 if ($user['import'])
160                         header('Location: '. site_url('user/account'));
161                 else
162                         header('Location: '. site_url());
163         }
164         
165         public function openid_policy()
166         {
167                 $this->load->view('openid_policy_view');
168         }
169         
170         /**
171          * Logout user and then redirect it to the last page which must be encoded
172          * in $redirect.
173          * 
174          * @param string $redirect      contains the last page URI segments encoded
175          * with helper url_encode_segments.
176          */
177         public function logout($redirect = '')
178         {
179                 $this->session->unset_userdata('user_id');
180                 $this->session->unset_userdata('username');
181                 $this->session->unset_userdata('auth_src');
182                 $this->session->unset_userdata('roles');
183                 $this->session->unset_userdata('time_zone');
184                 
185                 header('Location: '. site_url(urldecode_segments($redirect)));
186         }
187         
188         public function register($redirect = '')
189         {
190                 $this->load->library('form_validation');
191                 $this->load->helper('localization');
192                 $this->load->helper('date');
193                 
194                 $user_id = $this->session->userdata('user_id');
195                         
196                 $this->form_validation->set_error_delimiters('<span class="error">',
197                                         '</span>');
198                 $error_upload = '';
199
200                 if ($this->form_validation->run('register'))
201                 {
202                         $b_validation = TRUE;
203                         
204                         if ($_FILES['picture']['tmp_name'])
205                         {
206                                 // Upload library
207                                 $config_upload['upload_path'] = './data/user_pictures';
208                                 $config_upload['file_name'] = 
209                                         str_replace('.', '-', $this->input->post('username')) .'-';
210                                 $config_upload['allowed_types'] = 'gif|jpg|png';
211                                 $config_upload['max_size'] = '10240';
212                                 $this->load->library('upload', $config_upload);
213                                 
214                                 $b_validation = $this->upload->do_upload('picture');
215                                 $error_upload = 
216                                         $this->upload->display_errors('<span class="error">',
217                                                         '</span>');
218                         }
219                 }
220                 else
221                         $b_validation = FALSE;
222
223                 if (! $b_validation)
224                 {
225                         // Edit account data if logged in, otherwise register.
226                         // ** ACCOUNT
227                         if ($user_id)
228                         {
229                                 $userdata = $this->users_model->get_userdata(intval($user_id));
230                                 if (substr($userdata['username'], 0, 8) == 'autogen_')
231                                         $userdata['autogen_username'] =
232                                                 substr($userdata['username'], 8);
233                                 $selected_menu = 'account';
234                                 $captcha = FALSE;
235                         }
236                         // ** REGISTER
237                         else
238                         {
239                                 $userdata = FALSE;
240                                 $selected_menu = 'register';
241                                 
242                                 // CAPTCHA
243                                 $this->load->library('captcha');
244                                 $captcha = $this->captcha->get_captcha();
245                                 $captcha = $captcha['image'];
246                         }
247                         
248                         $params = array('title' =>
249                                                                 $this->lang->line('ui_nav_menu_register')
250                                                                         .' &ndash; '
251                                                                         . $this->config->item('site_name'),
252                                                         //'metas' => array('description'=>'')
253                         );
254                         $this->load->library('html_head_params', $params);
255                 
256                         // **
257                         // ** LOADING VIEWS
258                         // **
259                         $this->load->view('html_begin', $this->html_head_params);
260                         $this->load->view('header', 
261                                 array('selected_menu' => $selected_menu));
262                         
263                         $main_params['content'] = $this->load->view('user/register_view', 
264                                 array('userdata'=> $userdata, 'redirect'=> $redirect,
265                                         'error_upload'=> $error_upload, 'captcha'=> $captcha),
266                                 TRUE);
267                         $main_params['side'] = $this->load->view('side_default', NULL, TRUE);
268                         $this->load->view('main', $main_params);
269                 
270                         $this->load->view('footer');
271                         $this->load->view('html_end');
272                 }
273                 else
274                 {
275                         // TODO: Security problem!
276                         //$user_id = $this->input->post('user-id');
277                         if ($this->input->post('username'))
278                                 $data['username'] = $this->input->post('username');
279                         $data['email'] = $this->input->post('email');
280                         $data['first_name'] = $this->input->post('first-name');
281                         $data['last_name'] = $this->input->post('last-name');
282                         $data['sex'] = intval($this->input->post('sex'));
283                         $data['birth_date'] = $this->input->post('birth-date');
284                         $data['country'] = $this->input->post('country');
285                         $data['locality'] = $this->input->post('locality');
286                         $data['ui_lang'] = $this->input->post('ui-lang');
287                         $data['time_zone'] = $this->input->post('time-zone');
288                         
289                         // Handle picture if one was uploaded.
290                         if ($_FILES['picture']['tmp_name'])
291                         {
292                                 $upload_data = $this->upload->data();
293                                 $this->load->library('image');
294                                 $this->image->load($upload_data['full_path']);
295                                 // Resize original to a maximum size.
296                                 if ($this->image->get_width() * $this->image->get_height()
297                                                 > 640*480)
298                                 {
299                                         $this->image->save_thumbnail(
300                                                 $upload_data['full_path'],
301                                                 640, 480, IMAGETYPE_AUTO);
302                                 }
303                                 // Create thumbnail.
304                                 $data['picture'] = $upload_data['file_name'];
305                                 $this->image->save_thumbnail($upload_data['file_path']
306                                                 . $upload_data['file_name']. '-thumb.jpg', 120, 90);
307                         }
308                         
309                         // TODO: To much info as session data?
310                         // Update session user data.
311                         $this->_update_session_userdata($data);
312                         
313                         // Edit account data
314                         if ($user_id)
315                         {
316                                 $password = $this->input->post('new-password');
317                                 if ($password)
318                                         $data['password'] = $password;
319                                 
320                                 $this->users_model->set_userdata($user_id, $data);
321                                 
322                                 // Redirect to last page before login.
323                                 header('Location: '. site_url(urldecode_segments($redirect)));
324                         }
325                         // Registration
326                         else
327                         {
328                                 $data['username'] = $this->input->post('username');
329                                 $data['password'] = $this->input->post('password');
330                                 $data['auth_src'] = 'internal';
331                                 
332                                 $this->users_model->register($data);
333                                 $user_id = $this->users_model->get_userdata($data['username'],
334                                                 "id");
335                                 $user_id = $user_id['id'];
336                                 
337                                 // Redirect account activation page.
338                                 header('Location: '. site_url("user/activate/$user_id"));
339                         }
340                 }
341         }
342         
343         public function account($redirect = '')
344         {
345                 $this->register($redirect);
346         }
347         
348         public function profile($username, $videos_offset = 0)
349         {
350                 // TODO handle user not found
351                 
352                 $user_id = $this->session->userdata('user_id');
353                 if ($user_id)
354                 {
355                         if (intval($user_id) & USER_ROLE_ADMIN)
356                                 $allow_unactivated = TRUE;
357                         else
358                                 $allow_unactivated = FALSE;
359                 }
360                 else
361                         $allow_unactivated = FALSE;
362                 
363                 $this->load->config('localization');
364                 $this->load->helper('date');
365                 $this->lang->load('date');
366                 
367                 // **
368                 // ** LOADING MODEL
369                 // **
370                 // Logged in user time zone
371                 $time_zone = $this->session->userdata('time_zone');
372                 
373                 // User data
374                 $userdata = $this->users_model->get_userdata($username);
375                 $userdata['roles'] = Users_model::roles_to_string($userdata['roles']);
376                 $country_list = $this->config->item('country_list');
377                 $userdata['country_name'] = $country_list[ $userdata['country'] ];
378                 $userdata['last_login'] = human_gmt_to_human_local(
379                         $userdata['last_login'], $time_zone); 
380                 $userdata['time_zone'] = $this->lang->line($userdata['time_zone']);
381                 
382                 // User's videos
383                 $this->load->model('videos_model');
384                 $vs_data['videos'] = $this->videos_model->get_videos_summary(
385                                 NULL, $username, intval($videos_offset),
386                                 $this->config->item('videos_per_page'), 'hottest',
387                                 $allow_unactivated);
388                 
389                 // Pagination
390                 $this->load->library('pagination');
391                 $pg_config['base_url'] = site_url("user/profile/$username/");
392                 $pg_config['uri_segment'] = 4;
393                 $pg_config['total_rows'] = $this->videos_model->get_videos_count(
394                         NULL, $username, $allow_unactivated);
395                 $pg_config['per_page'] = $this->config->item('videos_per_page');
396                 $this->pagination->initialize($pg_config);
397                 $vs_data['pagination'] = $this->pagination->create_links();
398                 $vs_data['title'] = NULL;
399                 $vs_data['category_name'] = ''; // TODO videos_summary with AJAX
400                 
401                 $params = array(
402                         'title'=> $this->lang->line('user_appelation').' '.$username
403                                 .' &ndash; '
404                                 . $this->config->item('site_name'),
405                         'css'=> array('catalog.css')
406                         //'metas' => array('description'=>'')
407                 );
408                 $this->load->library('html_head_params', $params);
409                 
410                 // Current user profile tab
411                 $tab = (! $videos_offset ? 0 : 1);
412                 
413                 // **
414                 // ** LOADING VIEWS
415                 // **
416                 $this->load->view('html_begin', $this->html_head_params);
417                 $this->load->view('header', array());
418                 
419                 $vs = $this->load->view('catalog/videos_summary_view', $vs_data, TRUE);
420                 
421                 $main_params['content'] = $this->load->view('user/profile_view',
422                         array('userdata'=> $userdata, 'videos_summary'=> $vs, 'tab'=>$tab),
423                         TRUE);
424                 $main_params['side'] = $this->load->view('side_default', NULL, TRUE);
425                 $this->load->view('main', $main_params);
426                 
427                 $this->load->view('footer');
428                 $this->load->view('html_end');
429         }
430         
431         public function activate($user_id, $method='', $activation_code='')
432         {
433                 $user_id = intval($user_id);            
434                 $res_form_validation = FALSE;
435                 
436                 if ($method == 'code')
437                 {
438                         if (! $activation_code)
439                                 $res_form_validation = $this->form_validation->run('activate');
440                         // Activation code is provided in URL.
441                         else
442                         {
443                                 if ($this->_valid_activation_code($activation_code)
444                                                 && $this->users_model->activate_account($user_id,
445                                                         $activation_code))
446                                 {
447                                         $this->load->helper('message');
448                                         show_info_msg_page($this, sprintf(
449                                                 $this->lang->line('user_msg_activated_account'), 
450                                                 site_url('user/login')));
451                                         return;
452                                 }
453                                 else
454                                 {
455                                         $this->load->helper('message');
456                                         show_error_msg_page($this, 
457                                                         $this->lang->line(
458                                                                         'user_msg_wrong_activation_code'));
459                                         return;
460                                 }
461                         }
462                 }
463                 else if ($method == 'resend')
464                 {
465                         $res_form_validation =
466                                 $this->form_validation->run('resend_activation');
467                 }
468                 
469                 $userdata = $this->users_model->get_userdata($user_id,
470                                 'email, a.activation_code');
471                 $email = $userdata['email'];
472                 $activated_account = ($userdata['activation_code'] == NULL);
473                 
474                 if ($activated_account)
475                 {
476                         $this->load->helper('message');
477                         show_info_msg_page($this, sprintf(
478                                 $this->lang->line('user_msg_activated_account'), 
479                                 site_url('user/login')));
480                         return;
481                 }
482                 
483                 $this->load->library('form_validation');
484                         
485                 $this->form_validation->set_error_delimiters('<span class="error">',
486                                         '</span>');
487                 
488                 if ($res_form_validation === FALSE)
489                 {
490                         $params = array(
491                                 'title'=> $this->lang->line('user_title_activation')
492                                         .' &ndash; '
493                                         . $this->config->item('site_name'),
494                                 //'metas' => array('description'=>'')
495                         );
496                         $this->load->library('html_head_params', $params);
497                 
498                         // **
499                         // ** LOADING VIEWS
500                         // **
501                         $this->load->view('html_begin', $this->html_head_params);
502                         $this->load->view('header', array());
503
504                         // Show form
505                         $main_params['content'] = 
506                                 $this->load->view('user/activate_view',
507                                 array(  'user_id'=> $user_id,
508                                                 'email'=> $userdata['email']),
509                                 TRUE);
510                         
511                         $main_params['side'] = $this->load->view('side_default', NULL, TRUE);
512                         $this->load->view('main', $main_params);
513                 
514                         $this->load->view('footer');
515                         $this->load->view('html_end');
516                 }
517                 else
518                 {
519                         if ($method == 'code')
520                         {
521                                 // A message which tells the user that the
522                                 // activation was successful.
523                                 $this->load->helper('message');
524                                 show_info_msg_page($this, sprintf(
525                                         $this->lang->line('user_msg_activated_account'), 
526                                         site_url('user/login')));
527                                 return;
528                         }
529                         else if ($method == 'resend')
530                         {
531                                 // Redirect to resent message
532                                 $this->load->helper('message');
533                                 show_info_msg_page($this, sprintf(
534                                                 $this->lang->line('user_msg_activation_resent'),
535                                                 $this->input->post('email')));
536                                 return;
537                         }
538                 }
539         }
540         
541         public function recover_password()
542         {
543                 $this->load->library('form_validation');
544                         
545                 $this->form_validation->set_error_delimiters('<span class="error">',
546                         '</span>');
547
548                 if ($this->form_validation->run('recover_password') === FALSE)
549                 {
550                         $params = array(        'title' =>
551                                                                         $this->lang->line(
552                                                                                 'user_title_password_recovery')
553                                                                                 .' &ndash; '
554                                                                                 . $this->config->item('site_name'),
555                                                                 //'metas' => array('description'=>'')
556                         );
557                         $this->load->library('html_head_params', $params);
558                                 
559                         // **
560                         // ** LOADING VIEWS
561                         // **
562                         $this->load->view('html_begin', $this->html_head_params);
563                         $this->load->view('header', array('selected_menu' => 
564                                         'recover_password'));
565
566                         $main_params['content'] = $this->load->view(
567                                 'user/recover_password_view', array(),
568                                 TRUE);
569                         
570                         $main_params['side'] = $this->load->view('side_default', NULL, TRUE);
571                         $this->load->view('main', $main_params);
572                                 
573                         $this->load->view('footer');
574                         $this->load->view('html_end');
575                 }
576                 else
577                 {
578                         // Resent message
579                         $this->load->helper('message');
580                         show_info_msg_page($this, sprintf(
581                                         $this->lang->line('user_msg_password_recovery_email_sent'),
582                                         $this->input->post('username'),
583                                         $this->input->post('email')));
584                         return;
585                 }
586         }
587         
588         public function _format_message($msg, $val = '', $sub = '%s')
589         {
590                 return str_replace($sub, $val, $this->lang->line($msg));
591         }
592         
593         public function _update_session_userdata($data)
594         {
595                 foreach ($data as $key=> $val)
596                 {
597                         if ($this->session->userdata($key))
598                                 $this->session->set_userdata($key, $val);
599                 }
600         }
601         
602         public function _is_username_unique($username)
603         {
604                 if ($this->users_model->get_userdata($username))
605                         return FALSE;
606                 
607                 return TRUE;
608         }
609         
610         public function _valid_username($username)
611         {
612                 return (preg_match('/^[a-z0-9\._]+$/', $username) === 1);
613         }
614
615         public function _valid_username_or_email($username)
616         {
617                 $this->load->helper('email');
618
619                 if (valid_email($username))
620                         return TRUE;
621                 else
622                         return $this->_valid_username($username);
623         }
624         
625         public function _valid_date($date)
626         {
627                 if (! $date)
628                         return TRUE;
629                 
630                 return (preg_match('/[\d]{4}-[\d]{2}-[\d]{2}/', $date) === 1);
631         }
632         
633         public function _postprocess_birth_date($date)
634         {
635                 // If the user entered no birth date NULL needs to be inserted into DB.
636                 if (! $date)
637                         return NULL;
638                 
639                 return $date;
640         }
641         
642         public function _valid_old_password($old_password)
643         {
644                 if (! $old_password)
645                         return TRUE;
646                 
647                 $username= $this->session->userdata('username');
648                 
649                 if ($this->users_model->login($username, $old_password))
650                         return TRUE;
651                 
652                 return FALSE;
653         }
654         
655         public function _change_password_cond($param)
656         {
657                 $old = $this->input->post('old-password');
658                 $new = $this->input->post('new-password');
659                 $newc = $this->input->post('new-password-confirmation');
660                 
661                 return (!$old && !$new && !$newc)
662                         || ($old && $new && $newc);
663         }
664         
665         public function _required_by_register($param)
666         {
667                 $user_id = $this->session->userdata('user_id');
668                 
669                 if (! $user_id && ! $param)
670                         return FALSE;
671                 
672                 return TRUE;
673         }
674         
675         public function _valid_activation_code($activation_code)
676         {
677                 return (preg_match('/^[a-fA-F0-9]{16}$/', $activation_code) == 1);
678         }
679
680         public function _do_login($username, $field_password)
681         {
682                 $password = $this->input->post($field_password);
683
684                 $user = $this->users_model->login($username, $password);
685
686                 // Authentication failed.
687                 if ($user === FALSE)
688                         return FALSE;
689                 
690                 // User has not activated the account.
691                 if ($user['activation_code'] !== NULL)
692                 {
693                         $this->activated_account = FALSE;
694                         $this->user_id = $user['id'];
695                         return TRUE;
696                 }
697                 
698                 // Authentication successful: set session with user data.
699                 $this->session->set_userdata(array(
700                         'user_id'=> $user['id'],
701                         'username'=> $user['username'],
702                         'auth_src'=> $user['auth_src'],
703                         'roles'=> $user['roles'],
704                         'time_zone'=> $user['time_zone']
705                 ));
706                 $this->import = (isset($user['import']) ? $user['import'] : FALSE);
707                 return TRUE;
708         }
709         
710         public function _do_activate($activation_code)
711         {
712                 $user_id = $this->input->post('user-id');
713                 if ($user_id === FALSE)
714                         return FALSE;
715                 $user_id = intval($user_id);
716                 
717                 return $this->users_model->activate_account($user_id,
718                                 $activation_code);
719         }
720         
721         public function _do_resend_activation($email)
722         {
723                 $user_id = $this->input->post('user-id');
724                 if ($user_id === FALSE)
725                         return FALSE;
726                 $user_id = intval($user_id);
727                 
728                 $this->users_model->set_userdata($user_id,
729                         array('email'=> $email));
730                 
731                 return $this->users_model->send_activation_email($user_id, $email);
732         }
733         
734         public function _username_exists($username)
735         {
736                 $userdata = $this->users_model->get_userdata($username);
737                 
738                 if (! $userdata)
739                         return FALSE;
740                 
741                 return TRUE;
742         }
743         
744         public function _check_captcha($word)
745         {
746                 $this->load->library('captcha');
747                 
748                 return $this->captcha->check_captcha($word);
749         }
750         
751         public function _internal_account($username)
752         {
753                 $userdata = $this->users_model->get_userdata($username, 'auth_src');
754                 if (! $userdata)
755                         return FALSE;
756
757                 if ($userdata['auth_src'] != 'internal')
758                         return FALSE;
759                 
760                 return TRUE;
761         }
762         
763         public function _do_recover_password($username)
764         {
765                 $email = $this->input->post('email');
766                 if (! $email)
767                         return FALSE;
768                 
769                 return $this->users_model->recover_password($username, $email);
770         }
771 }
772
773 /* End of file user.php */
774 /* Location: ./application/controllers/user.php */