]> git.mxchange.org Git - pizzaservice-war.git/blob - src/java/org/mxchange/pizzaapplication/beans/user/PizzaUserWebRequestBean.java
Please cherry-pick:
[pizzaservice-war.git] / src / java / org / mxchange / pizzaapplication / beans / user / PizzaUserWebRequestBean.java
1 /*
2  * Copyright (C) 2016, 2017 Roland Häder
3  *
4  * This program is free software: you can redistribute it and/or modify
5  * it under the terms of the GNU Affero General Public License as
6  * published by the Free Software Foundation, either version 3 of the
7  * License, or (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU Affero General Public License for more details.
13  *
14  * You should have received a copy of the GNU Affero General Public License
15  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
16  */
17 package org.mxchange.pizzaapplication.beans.user;
18
19 import fish.payara.cdi.jsr107.impl.NamedCache;
20 import java.text.MessageFormat;
21 import java.util.Iterator;
22 import java.util.LinkedList;
23 import java.util.List;
24 import java.util.Locale;
25 import java.util.Objects;
26 import javax.annotation.PostConstruct;
27 import javax.cache.Cache;
28 import javax.ejb.EJB;
29 import javax.enterprise.context.RequestScoped;
30 import javax.enterprise.event.Event;
31 import javax.enterprise.event.Observes;
32 import javax.enterprise.inject.Any;
33 import javax.faces.context.FacesContext;
34 import javax.faces.view.facelets.FaceletException;
35 import javax.inject.Inject;
36 import javax.inject.Named;
37 import org.mxchange.jcontacts.model.contact.Contact;
38 import org.mxchange.jcoreee.events.locale.ObservableLocaleChangeEvent;
39 import org.mxchange.jusercore.events.user.add.ObservableAdminAddedUserEvent;
40 import org.mxchange.jusercore.events.user.clear.password.ObservableClearUserPasswordEvent;
41 import org.mxchange.jusercore.events.user.clear.username.ObservableClearUserNameEvent;
42 import org.mxchange.jusercore.events.user.created.ObservableCreatedUserEvent;
43 import org.mxchange.jusercore.events.user.delete.ObservableAdminDeletedUserEvent;
44 import org.mxchange.jusercore.events.user.linked.ObservableAdminLinkedUserEvent;
45 import org.mxchange.jusercore.events.user.locked.ObservableAdminLockedUserEvent;
46 import org.mxchange.jusercore.events.user.unlocked.ObservableAdminUnlockedUserEvent;
47 import org.mxchange.jusercore.events.user.update.ObservableAdminUpdatedUserDataEvent;
48 import org.mxchange.jusercore.events.user.update.ObservableUpdatedUserPersonalDataEvent;
49 import org.mxchange.jusercore.events.user.update.UpdatedUserPersonalDataEvent;
50 import org.mxchange.jusercore.exceptions.UserEmailAddressNotFoundException;
51 import org.mxchange.jusercore.exceptions.UserNotFoundException;
52 import org.mxchange.jusercore.model.user.LoginUser;
53 import org.mxchange.jusercore.model.user.User;
54 import org.mxchange.jusercore.model.user.UserSessionBeanRemote;
55 import org.mxchange.jusercore.model.user.profilemodes.ProfileMode;
56 import org.mxchange.juserlogincore.events.confirmation.ObservableUserConfirmedAccountEvent;
57 import org.mxchange.juserlogincore.events.login.ObservableUserLoggedInEvent;
58 import org.mxchange.juserlogincore.events.registration.ObservableUserRegisteredEvent;
59 import org.mxchange.juserlogincore.events.user.password_change.ObservableUpdatedUserPasswordEvent;
60 import org.mxchange.juserlogincore.exceptions.UserPasswordMismatchException;
61 import org.mxchange.juserlogincore.login.UserLoginUtils;
62 import org.mxchange.pizzaapplication.beans.BasePizzaController;
63 import org.mxchange.pizzaapplication.beans.contact.PizzaContactWebRequestController;
64 import org.mxchange.pizzaapplication.beans.features.PizzaFeaturesWebApplicationController;
65 import org.mxchange.pizzaapplication.beans.localization.PizzaLocalizationSessionController;
66 import org.mxchange.pizzaapplication.beans.user.login.PizzaUserLoginWebSessionController;
67
68 /**
69  * A user bean (controller)
70  * <p>
71  * @author Roland Häder<roland@mxchange.org>
72  */
73 @Named ("userController")
74 @RequestScoped
75 public class PizzaUserWebRequestBean extends BasePizzaController implements PizzaUserWebRequestController {
76
77         /**
78          * Serial number
79          */
80         private static final long serialVersionUID = 542_145_347_916L;
81
82         /**
83          * General contact controller
84          */
85         @Inject
86         private PizzaContactWebRequestController contactController;
87
88         /**
89          * Features controller
90          */
91         @Inject
92         private PizzaFeaturesWebApplicationController featureController;
93
94         /**
95          * Locale instance
96          */
97         private Locale locale;
98
99         /**
100          * Localization controller
101          */
102         @Inject
103         private PizzaLocalizationSessionController localizationController;
104
105         /**
106          * Event being fired when user updated personal data
107          */
108         @Inject
109         @Any
110         private Event<ObservableUpdatedUserPersonalDataEvent> updatedPersonalDataEvent;
111
112         /**
113          * Remote user bean
114          */
115         @EJB (lookup = "java:global/jfinancials-ejb/user!org.mxchange.jusercore.model.user.UserSessionBeanRemote")
116         private UserSessionBeanRemote userBean;
117
118         /**
119          * A list of all user profiles
120          */
121         @Inject
122         @NamedCache (cacheName = "userCache", managementEnabled = true)
123         private transient Cache<Long, User> userCache;
124
125         /**
126          * User id
127          */
128         private Long userId;
129
130         /**
131          * Login controller (bean)
132          */
133         @Inject
134         private PizzaUserLoginWebSessionController userLoginController;
135
136         /**
137          * User name
138          */
139         private String userName;
140
141         /**
142          * User name list
143          */
144         @Inject
145         @NamedCache (cacheName = "userNameCache", managementEnabled = true)
146         private transient Cache<Long, String> userNameCache;
147
148         /**
149          * User password (clear-text from web form)
150          */
151         private String userPassword;
152
153         /**
154          * User password repeated (clear-text from web form)
155          */
156         private String userPasswordRepeat;
157
158         /**
159          * Whether the user wants a public profile
160          */
161         private ProfileMode userProfileMode;
162
163         /**
164          * Default constructor
165          */
166         public PizzaUserWebRequestBean () {
167                 // Call super constructor
168                 super();
169         }
170
171         /**
172          * Event observer for newly added users by administrator
173          * <p>
174          * @param event Event being fired
175          */
176         public void afterAdminAddedUserEvent (@Observes final ObservableAdminAddedUserEvent event) {
177                 // event should not be null
178                 if (null == event) {
179                         // Throw NPE
180                         throw new NullPointerException("event is null"); //NOI18N
181                 } else if (event.getAddedUser() == null) {
182                         // Throw NPE again
183                         throw new NullPointerException("event.addedUser is null"); //NOI18N
184                 } else if (event.getAddedUser().getUserId() == null) {
185                         // userId is null
186                         throw new NullPointerException("event.addedUser.userId is null"); //NOI18N
187                 } else if (event.getAddedUser().getUserId() < 1) {
188                         // Not avalid id
189                         throw new IllegalArgumentException(MessageFormat.format("userId of user={0} is not valid: {1}", event.getAddedUser(), event.getAddedUser().getUserId())); //NOI18N
190                 }
191
192                 // Update user list
193                 this.updateList(event.getAddedUser());
194
195                 // Clear all data
196                 this.clear();
197
198                 // Set user id again
199                 this.setUserId(event.getAddedUser().getUserId());
200         }
201
202         /**
203          * Event observer for deleted user accounts (by administrator)
204          * <p>
205          * @param event Event being fired
206          */
207         public void afterAdminDeletedUserEvent (@Observes final ObservableAdminDeletedUserEvent event) {
208                 // event should not be null
209                 if (null == event) {
210                         // Throw NPE
211                         throw new NullPointerException("event is null"); //NOI18N
212                 } else if (event.getDeletedUser() == null) {
213                         // Throw NPE again
214                         throw new NullPointerException("event.deletedUser is null"); //NOI18N
215                 } else if (event.getDeletedUser().getUserId() == null) {
216                         // userId is null
217                         throw new NullPointerException("event.deletedUser.userId is null"); //NOI18N
218                 } else if (event.getDeletedUser().getUserId() < 1) {
219                         // Not avalid id
220                         throw new IllegalArgumentException(MessageFormat.format("userId of user={0} is not valid: {1}", event.getDeletedUser(), event.getDeletedUser().getUserId())); //NOI18N
221                 }
222
223                 // Update user list
224                 this.removeFromList(event.getDeletedUser());
225
226                 // Clear all data
227                 this.clear();
228         }
229
230         /**
231          * Event observer for linked users with existing contact data
232          * <p>
233          * @param event Event being fired
234          */
235         public void afterAdminLinkedUserEvent (@Observes final ObservableAdminLinkedUserEvent event) {
236                 // event should not be null
237                 if (null == event) {
238                         // Throw NPE
239                         throw new NullPointerException("event is null"); //NOI18N
240                 } else if (event.getLinkedUser() == null) {
241                         // Throw NPE again
242                         throw new NullPointerException("event.linkedUser is null"); //NOI18N
243                 } else if (event.getLinkedUser().getUserId() == null) {
244                         // userId is null
245                         throw new NullPointerException("event.linkedUser.userId is null"); //NOI18N
246                 } else if (event.getLinkedUser().getUserId() < 1) {
247                         // Not avalid id
248                         throw new IllegalArgumentException(MessageFormat.format("userId of user={0} is not valid: {1}", event.getLinkedUser(), event.getLinkedUser().getUserId())); //NOI18N
249                 }
250
251                 // Update user list
252                 this.updateList(event.getLinkedUser());
253
254                 // Clear all data
255                 this.clear();
256
257                 // Set user id again
258                 this.setUserId(event.getLinkedUser().getUserId());
259         }
260
261         /**
262          * Event observer for locked users
263          * <p>
264          * @param event Event being fired
265          */
266         public void afterAdminLockedUserEvent (@Observes final ObservableAdminLockedUserEvent event) {
267                 // event should not be null
268                 if (null == event) {
269                         // Throw NPE
270                         throw new NullPointerException("event is null"); //NOI18N
271                 } else if (event.getLockedUser() == null) {
272                         // Throw NPE again
273                         throw new NullPointerException("event.lockedUser is null"); //NOI18N
274                 } else if (event.getLockedUser().getUserId() == null) {
275                         // userId is null
276                         throw new NullPointerException("event.lockedUser.userId is null"); //NOI18N
277                 } else if (event.getLockedUser().getUserId() < 1) {
278                         // Not avalid id
279                         throw new IllegalArgumentException(MessageFormat.format("userId of user={0} is not valid: {1}", event.getLockedUser(), event.getLockedUser().getUserId())); //NOI18N
280                 }
281
282                 // Update user list
283                 this.updateList(event.getLockedUser());
284         }
285
286         /**
287          * Event observer for unlocked users
288          * <p>
289          * @param event Event being fired
290          */
291         public void afterAdminUnlockedUserEvent (@Observes final ObservableAdminUnlockedUserEvent event) {
292                 // event should not be null
293                 if (null == event) {
294                         // Throw NPE
295                         throw new NullPointerException("event is null"); //NOI18N
296                 } else if (event.getUnlockedUser() == null) {
297                         // Throw NPE again
298                         throw new NullPointerException("event.unlockedUser is null"); //NOI18N
299                 } else if (event.getUnlockedUser().getUserId() == null) {
300                         // userId is null
301                         throw new NullPointerException("event.unlockedUser.userId is null"); //NOI18N
302                 } else if (event.getUnlockedUser().getUserId() < 1) {
303                         // Not avalid id
304                         throw new IllegalArgumentException(MessageFormat.format("userId of user={0} is not valid: {1}", event.getUnlockedUser(), event.getUnlockedUser().getUserId())); //NOI18N
305                 }
306
307                 // Update user list
308                 this.updateList(event.getUnlockedUser());
309         }
310
311         /**
312          * Event observer for updated user data by administrator
313          * <p>
314          * @param event Event being updated
315          */
316         public void afterAdminUpdatedUserDataEvent (@Observes final ObservableAdminUpdatedUserDataEvent event) {
317                 // event should not be null
318                 if (null == event) {
319                         // Throw NPE
320                         throw new NullPointerException("event is null"); //NOI18N
321                 } else if (event.getUpdatedUser() == null) {
322                         // Throw NPE again
323                         throw new NullPointerException("event.updatedUser is null"); //NOI18N
324                 } else if (event.getUpdatedUser().getUserId() == null) {
325                         // userId is null
326                         throw new NullPointerException("event.updatedUser.userId is null"); //NOI18N
327                 } else if (event.getUpdatedUser().getUserId() < 1) {
328                         // Not avalid id
329                         throw new IllegalArgumentException(MessageFormat.format("userId of user={0} is not valid: {1}", event.getUpdatedUser(), event.getUpdatedUser().getUserId())); //NOI18N
330                 }
331
332                 // Update user list
333                 this.updateList(event.getUpdatedUser());
334
335                 // Clear all data
336                 this.clear();
337         }
338
339         /**
340          * Event observer for when a bean helper has successfully created a user
341          * instance, means the user exists. If the user does not exist, this event
342          * should not fire but instead a proper exception must be thrown.
343          * <p>
344          * @param event User created event
345          */
346         public void afterCreatedUserEvent (@Observes final ObservableCreatedUserEvent event) {
347                 // Is the instance valid?
348                 if (null == event) {
349                         // Throw NPE
350                         throw new NullPointerException("event is null"); //NOI18N
351                 } else if (event.getCreatedUser() == null) {
352                         // Throw NPE again
353                         throw new NullPointerException("event.createdUser is null"); //NOI18N
354                 } else if (event.getCreatedUser().getUserId() == null) {
355                         // Throw NPE again
356                         throw new NullPointerException("event.createdUser.userId is null"); //NOI18N
357                 } else if (event.getCreatedUser().getUserId() < 1) {
358                         // Throw NPE again
359                         throw new NullPointerException(MessageFormat.format("event.createdUser.userId={0} is not valid", event.getCreatedUser().getUserId())); //NOI18N
360                 }
361
362                 // Get user instance
363                 User user = event.getCreatedUser();
364
365                 // Set all fields here
366                 this.copyUser(user);
367         }
368
369         /**
370          * Observer method for events being fired when the application's locale has
371          * been changed.
372          * <p>
373          * @param event Event being fired
374          */
375         public void afterLocaleChangeEvent (@Observes final ObservableLocaleChangeEvent event) {
376                 // Is the parameter valid?
377                 if (null == event) {
378                         // Throw NPE
379                         throw new NullPointerException("event is null");
380                 } else if (event.getLocale() == null) {
381                         // Throw NPE again
382                         throw new NullPointerException("event.locale is null");
383                 }
384
385                 // Set it here
386                 this.setLocale(event.getLocale());
387         }
388
389         /**
390          * Event observer when user confirmed account.
391          * <p>
392          * @param event Event being fired
393          */
394         public void afterUserConfirmedAccountEvent (@Observes final ObservableUserConfirmedAccountEvent event) {
395                 // event should not be null
396                 if (null == event) {
397                         // Throw NPE
398                         throw new NullPointerException("event is null"); //NOI18N
399                 } else if (event.getConfirmedUser() == null) {
400                         // Throw NPE again
401                         throw new NullPointerException("event.confirmedUser is null"); //NOI18N
402                 } else if (event.getConfirmedUser().getUserId() == null) {
403                         // userId is null
404                         throw new NullPointerException("event.confirmedUser.userId is null"); //NOI18N
405                 } else if (event.getConfirmedUser().getUserId() < 1) {
406                         // Not avalid id
407                         throw new IllegalArgumentException(MessageFormat.format("userId of user={0} is not valid: {1}", event.getConfirmedUser(), event.getConfirmedUser().getUserId())); //NOI18N
408                 }
409
410                 // Update user list
411                 this.updateList(event.getConfirmedUser());
412         }
413
414         /**
415          * Event observer for logged-in user
416          * <p>
417          * @param event Event instance
418          */
419         public void afterUserLoginEvent (@Observes final ObservableUserLoggedInEvent event) {
420                 // event should not be null
421                 if (null == event) {
422                         // Throw NPE
423                         throw new NullPointerException("event is null"); //NOI18N
424                 } else if (event.getLoggedInUser() == null) {
425                         // Throw NPE again
426                         throw new NullPointerException("event.registeredUser is null"); //NOI18N
427                 } else if (event.getLoggedInUser().getUserId() == null) {
428                         // userId is null
429                         throw new NullPointerException("event.registeredUser.userId is null"); //NOI18N
430                 } else if (event.getLoggedInUser().getUserId() < 1) {
431                         // Not avalid id
432                         throw new IllegalArgumentException(MessageFormat.format("userId of user={0} is not valid: {1}", event.getLoggedInUser(), event.getLoggedInUser().getUserId())); //NOI18N
433                 }
434
435                 // "Cache" user instance
436                 User loggedInUser = event.getLoggedInUser();
437
438                 // Copy all data to this bean
439                 this.copyUser(loggedInUser);
440         }
441
442         /**
443          * Event observer for user password changes
444          * <p>
445          * @param event Event being fired
446          */
447         public void afterUserPasswordChangedEvent (@Observes final ObservableUpdatedUserPasswordEvent event) {
448                 // Is it valid?
449                 if (null == event) {
450                         // Throw NPE
451                         throw new NullPointerException("event is null"); //NOI18N
452                 } else if (event.getUserPassword() == null) {
453                         // Throw NPE
454                         throw new NullPointerException("event.userPassword is null"); //NOI18N
455                 } else if (event.getUserPassword().isEmpty()) {
456                         // Throw NPE
457                         throw new IllegalArgumentException("event.userPassword is empty"); //NOI18N
458                 }
459
460                 // Set it here
461                 this.setUserPassword(event.getUserPassword());
462                 this.setUserPasswordRepeat(event.getUserPassword());
463         }
464
465         /**
466          * Event observer for new user registrations
467          * <p>
468          * @param event User registration event
469          */
470         public void afterUserRegistrationEvent (@Observes final ObservableUserRegisteredEvent event) {
471                 // event should not be null
472                 if (null == event) {
473                         // Throw NPE
474                         throw new NullPointerException("event is null"); //NOI18N
475                 } else if (event.getRegisteredUser() == null) {
476                         // Throw NPE again
477                         throw new NullPointerException("event.registeredUser is null"); //NOI18N
478                 } else if (event.getRegisteredUser().getUserId() == null) {
479                         // userId is null
480                         throw new NullPointerException("event.registeredUser.userId is null"); //NOI18N
481                 } else if (event.getRegisteredUser().getUserId() < 1) {
482                         // Not avalid id
483                         throw new IllegalArgumentException(MessageFormat.format("userId of user={0} is not valid: {1}", event.getRegisteredUser(), event.getRegisteredUser().getUserId())); //NOI18N
484                 }
485
486                 // Get user instance
487                 User registeredUser = event.getRegisteredUser();
488
489                 // Copy all data from registered->user
490                 this.copyUser(registeredUser);
491
492                 // Clear all data
493                 this.clear();
494
495                 // Update user list
496                 this.updateList(registeredUser);
497
498                 // Add user name
499                 this.addUserName(registeredUser);
500
501                 // Set user id again
502                 this.setUserId(registeredUser.getUserId());
503         }
504
505         /**
506          * Method being call after user's password has been updated (and history
507          * entry has been created).
508          * <p>
509          * @param event Event being observed
510          */
511         public void afterUserUpdatedPasswordEvent (@Observes final ObservableUpdatedUserPasswordEvent event) {
512                 // Check parameter
513                 if (null == event) {
514                         // Throw NPE
515                         throw new NullPointerException("event is null"); //NOI18N
516                 } else if (event.getPasswordHistory() == null) {
517                         // Throw NPE again
518                         throw new NullPointerException("event.passwordHistory is null"); //NOI18N
519                 } else if (event.getPasswordHistory().getUserPasswordHistoryId() == null) {
520                         // ... and again
521                         throw new NullPointerException("event.passwordHistory.userPasswordHistoryId is null"); //NOI18N
522                 } else if (event.getPasswordHistory().getUserPasswordHistoryId() < 1) {
523                         // Invalid value
524                         throw new IllegalArgumentException(MessageFormat.format("event.passwordHistory.userPasswordHistoryId={0} is in valid", event.getPasswordHistory().getUserPasswordHistoryId())); //NOI18N
525                 }
526
527                 // Update user list
528                 this.updateList(event.getPasswordHistory().getUserPasswordHistoryUser());
529         }
530
531         /**
532          * Listens to fired event when user updated personal data
533          * <p>
534          * @param event Event being fired
535          */
536         public void afterUserUpdatedPersonalDataEvent (@Observes final ObservableUpdatedUserPersonalDataEvent event) {
537                 // Check parameter
538                 if (null == event) {
539                         // Throw NPE
540                         throw new NullPointerException("event is null"); //NOI18N
541                 } else if (event.getUpdatedUser() == null) {
542                         // Throw NPE again
543                         throw new NullPointerException("event.updatedUser is null"); //NOI18N
544                 } else if (event.getUpdatedUser().getUserId() == null) {
545                         // ... and again
546                         throw new NullPointerException("event.updatedUser.userId is null"); //NOI18N
547                 } else if (event.getUpdatedUser().getUserId() < 1) {
548                         // Invalid value
549                         throw new IllegalArgumentException(MessageFormat.format("event.updatedUser.userId={0} is in valid", event.getUpdatedUser().getUserId())); //NOI18N
550                 }
551
552                 // Update user list
553                 this.updateList(event.getUpdatedUser());
554         }
555
556         @Override
557         @SuppressWarnings ("ReturnOfCollectionOrArrayField")
558         public List<User> allUsers () {
559                 // Init list
560                 List<User> list = new LinkedList<>();
561
562                 // Get iterator
563                 Iterator<Cache.Entry<Long, User>> iterator = this.userCache.iterator();
564
565                 // Loop over all
566                 while (iterator.hasNext()) {
567                         // Get next entry
568                         final Cache.Entry<Long, User> next = iterator.next();
569
570                         // Add value to list
571                         list.add(next.getValue());
572                 }
573
574                 // Return it
575                 return list;
576         }
577
578         /**
579          * Event observer for when a user name should be cleared
580          * <p>
581          * @param event Event being fired
582          */
583         public void clearUserNameEvent (@Observes final ObservableClearUserNameEvent event) {
584                 // Is it valid?
585                 if (null == event) {
586                         // Throw NPE
587                         throw new NullPointerException("event is null");
588                 }
589
590                 // Clear it
591                 this.clearUserName();
592         }
593
594         /**
595          * Event observer for when both user passwords should be cleared
596          * <p>
597          * @param event Event being fired
598          */
599         public void clearUserPasswordEvent (@Observes final ObservableClearUserPasswordEvent event) {
600                 // Is it valid?
601                 if (null == event) {
602                         // Throw NPE
603                         throw new NullPointerException("event is null");
604                 }
605
606                 // Clear it
607                 this.clearUserPasswords();
608         }
609
610         @Override
611         public User createUserInstance (final boolean createContactData) {
612                 // Trace message
613                 //* NOISY-DEBUG: */ System.out.println(MessageFormat.format("{0}.createUserInstance: CALLED!", this.getClass().getSimpleName()));
614
615                 // Required personal data must be set
616                 assert (this.isRequiredPersonalDataSet()) : "not all personal data is set"; //NOI18N
617
618                 // Create new user instance
619                 User user = new LoginUser();
620
621                 // Is user name required?
622                 if (!this.isUserNameRequired()) {
623                         // Generate pseudo-random user name
624                         String randomName = this.userBean.generateRandomUserName();
625
626                         // Set it and inivisible profile
627                         this.setUserName(randomName);
628                         this.setUserProfileMode(ProfileMode.INVISIBLE);
629
630                         // Generate random password
631                         String randomPassword = UserLoginUtils.createRandomPassword(PizzaUserWebRequestController.MINIMUM_PASSWORD_LENGTH);
632
633                         // Set random password
634                         this.setUserPassword(randomPassword);
635                         this.setUserPasswordRepeat(randomPassword);
636                 }
637
638                 // Set user name profile mode and locale
639                 user.setUserName(this.getUserName());
640                 user.setUserProfileMode(this.getUserProfileMode());
641                 user.setUserLocale(this.getLocale());
642
643                 // Is multiple registration page
644                 if ((createContactData) || (!this.featureController.isFeatureEnabled("user_register_multiple_page"))) { //NOI18N
645                         // Create contact instance
646                         Contact contact = this.contactController.createContactInstance();
647
648                         // Debug message
649                         //* NOISY-DEBUG: */ System.out.println(MessageFormat.format("{0}.createUserInstance: contact={1}", this.getClass().getSimpleName(), contact));
650                         // Set contact in user
651                         user.setUserContact(contact);
652                 }
653
654                 // Trace message
655                 //* NOISY-DEBUG: */ System.out.println(MessageFormat.format("{0}.createUserInstance: user={1} - EXIT!", this.getClass().getSimpleName(), user));
656                 // Return it
657                 return user;
658         }
659
660         @Override
661         public User createUserLogin () {
662                 // Trace message
663                 //* NOISY-DEBUG */ System.out.println(MessageFormat.format("{0}.createUserLogin: CALLED!", this.getClass().getSimpleName()));
664
665                 // Is all data set?
666                 if (this.getUserName() == null) {
667                         // Throw NPE
668                         throw new NullPointerException("userName is null"); //NOI18N
669                 } else if (this.getUserName().isEmpty()) {
670                         // Is empty
671                         throw new IllegalStateException("userName is empty."); //NOI18N
672                 }
673
674                 // Create new user instance
675                 User user = new LoginUser();
676
677                 // Update all data ...
678                 user.setUserName(this.getUserName());
679
680                 // Trace message
681                 //* NOISY-DEBUG */ System.out.println(MessageFormat.format("{0}.createUserLogin: user={1} - EXIT!", this.getClass().getSimpleName(), user));
682                 // Return the new instance
683                 return user;
684         }
685
686         @Override
687         public String doChangePersonalData () {
688                 // This method shall only be called if the user is logged-in
689                 if (!this.userLoginController.isUserLoggedIn()) {
690                         // Not logged-in
691                         throw new IllegalStateException("User is not logged-in"); //NOI18N
692                 } else if (!this.isRequiredChangePersonalDataSet()) {
693                         // Not all required fields are set
694                         throw new FaceletException("Not all required fields are set."); //NOI18N
695                 } else if (!this.userLoginController.ifCurrentPasswordMatches()) {
696                         // Password not matching
697                         throw new FaceletException(new UserPasswordMismatchException(this.userLoginController.getLoggedInUser()));
698                 } else if (!this.featureController.isFeatureEnabled("change_user_personal_data")) { //NOI18N
699                         // Editing is not allowed
700                         throw new IllegalStateException("User tried to edit personal data."); //NOI18N
701                 }
702
703                 // Get user instance
704                 User user = this.userLoginController.getLoggedInUser();
705
706                 // Copy contact data to contact instance
707                 this.contactController.updateContactDataFromController(user.getUserContact());
708
709                 // It should be there, so run some tests on it
710                 assert (user instanceof User) : "Instance userLoginController.loggedInUser is null"; //NOI18N
711                 assert (user.getUserId() instanceof Long) : "Instance userLoginController.loggedInUser.userId is null"; //NOI18N
712                 assert (user.getUserId() > 0) : MessageFormat.format("userLoginController.loggedInUser.userId={0} is invalid", user.getUserId()); //NOI18N
713                 assert (user.getUserContact() instanceof Contact) : "Instance userLoginController.loggedInUser.userContact is null"; //NOI18N
714                 assert (user.getUserContact().getContactId() instanceof Long) : "Instance userLoginController.userContact.contactId is null"; //NOI18N
715                 assert (user.getUserContact().getContactId() > 0) : MessageFormat.format("Instance userLoginController.userContact.contactId={0} is invalid", user.getUserContact().getContactId()); //NOI18N
716
717                 // Update all fields
718                 user.setUserProfileMode(this.getUserProfileMode());
719
720                 // Send it to the EJB
721                 User updatedUser = this.userBean.updateUserPersonalData(user);
722
723                 // Fire event
724                 this.updatedPersonalDataEvent.fire(new UpdatedUserPersonalDataEvent(updatedUser));
725
726                 // All fine
727                 return "user_contact_data_saved"; //NOI18N
728         }
729
730         /**
731          * Getter for user id
732          * <p>
733          * @return User id
734          */
735         public Long getUserId () {
736                 return this.userId;
737         }
738
739         /**
740          * Setter for user id
741          * <p>
742          * @param userId User id
743          */
744         public void setUserId (final Long userId) {
745                 this.userId = userId;
746         }
747
748         /**
749          * Getter for user name
750          * <p>
751          * @return User name
752          */
753         public String getUserName () {
754                 return this.userName;
755         }
756
757         /**
758          * Setter for user name
759          * <p>
760          * @param userName User name
761          */
762         public void setUserName (final String userName) {
763                 this.userName = userName;
764         }
765
766         @Override
767         public String getUserPassword () {
768                 return this.userPassword;
769         }
770
771         /**
772          * Setter for clear-text user password
773          * <p>
774          * @param userPassword Clear-text user password
775          */
776         public void setUserPassword (final String userPassword) {
777                 this.userPassword = userPassword;
778         }
779
780         /**
781          * Getter for clear-text user password repeated
782          * <p>
783          * @return Clear-text user password repeated
784          */
785         public String getUserPasswordRepeat () {
786                 return this.userPasswordRepeat;
787         }
788
789         /**
790          * Setter for clear-text user password repeated
791          * <p>
792          * @param userPasswordRepeat Clear-text user password repeated
793          */
794         public void setUserPasswordRepeat (final String userPasswordRepeat) {
795                 this.userPasswordRepeat = userPasswordRepeat;
796         }
797
798         /**
799          * Getter for user profile mode
800          * <p>
801          * @return User profile mode
802          */
803         public ProfileMode getUserProfileMode () {
804                 return this.userProfileMode;
805         }
806
807         /**
808          * Setter for user profile mode
809          * <p>
810          * @param userProfileMode User profile mode
811          */
812         public void setUserProfileMode (final ProfileMode userProfileMode) {
813                 this.userProfileMode = userProfileMode;
814         }
815
816         @Override
817         public boolean ifBothPasswordsEmptyAllowed () {
818                 // Check feature first
819                 return ((this.featureController.isFeatureEnabled("allow_user_registration_empty_password")) && //NOI18N
820                                 ((this.getUserPassword() == null) || (this.getUserPassword().isEmpty())) &&
821                                 ((this.getUserPasswordRepeat() == null) || (this.getUserPasswordRepeat().isEmpty())));
822         }
823
824         /**
825          * Post-initialization of this class
826          */
827         @PostConstruct
828         public void init () {
829                 // Is cache there?
830                 if (!this.userCache.iterator().hasNext()) {
831                         // Get whole list
832                         List<User> list = this.userBean.allUsers();
833
834                         // Add all
835                         for (final Iterator<User> iterator = list.iterator(); iterator.hasNext();) {
836                                 // Get next element
837                                 final User next = iterator.next();
838
839                                 // Add it to cache
840                                 this.userCache.put(next.getUserId(), next);
841                                 this.userNameCache.put(next.getUserId(), next.getUserName());
842                         }
843                 }
844         }
845
846         @Override
847         public boolean isContactFound (final Contact contact) {
848                 // The contact must be valid
849                 if (null == contact) {
850                         // Throw NPE
851                         throw new NullPointerException("contact is null"); //NOI18N
852                 } else if (contact.getContactId() == null) {
853                         // Throw again ...
854                         throw new NullPointerException("contact.contactId is null"); //NOI18N
855                 } else if (contact.getContactId() < 1) {
856                         // Not valid
857                         throw new IllegalArgumentException(MessageFormat.format("contact.contactId={0} is not valid", contact.getContactId())); //NOI18N
858                 }
859
860                 // Default is not found
861                 boolean isFound = false;
862
863                 // Get iterator
864                 Iterator<User> iterator = this.allUsers().iterator();
865
866                 // Loop through all entries
867                 while (iterator.hasNext()) {
868                         // Get user
869                         User next = iterator.next();
870
871                         // Compare both objects
872                         if (Objects.equals(contact, next.getUserContact())) {
873                                 // Found it
874                                 isFound = true;
875                                 break;
876                         }
877                 }
878
879                 // Return status
880                 return isFound;
881         }
882
883         @Override
884         public boolean isPublicUserProfileEnabled () {
885                 // Get context parameter
886                 String contextParameter = FacesContext.getCurrentInstance().getExternalContext().getInitParameter("is_public_profile_enabled"); //NOI18N
887
888                 // Is it set?
889                 boolean isEnabled = ((contextParameter instanceof String) && (contextParameter.toLowerCase().equals("true"))); //NOI18N
890
891                 // This requires user names being enabled, too.
892                 if ((isEnabled) && (!this.isUserNameRequired())) {
893                         // Not valid state, users must be able to modify their profile, especially when it is public
894                         throw new IllegalStateException("Public user profiles are enabled but user name requirement is disabled, this is not possible."); //NOI18N
895                 }
896
897                 // Return value
898                 return isEnabled;
899         }
900
901         @Override
902         public boolean isRequiredChangePersonalDataSet () {
903                 return ((this.getUserProfileMode() != null) &&
904                                 (this.getUserName() != null) && (!this.getUserName().isEmpty()) &&
905                                 (this.contactController.isRequiredChangePersonalDataSet()));
906         }
907
908         @Override
909         public boolean isRequiredPersonalDataSet () {
910                 if (this.featureController.isFeatureEnabled("user_register_multiple_page")) { //NOI18N
911                         // Multiple registration page
912                         return this.contactController.isRequiredPersonalDataSet();
913                 } else {
914                         // Single registration page
915                         return (((this.getUserName() != null) || (!this.isUserNameRequired())) &&
916                                         (this.getUserProfileMode() != null) &&
917                                         (this.contactController.isRequiredPersonalDataSet()) &&
918                                         (this.getUserPassword() != null) &&
919                                         (this.getUserPasswordRepeat() != null));
920                 }
921         }
922
923         @Override
924         public boolean isSamePasswordEntered () {
925                 return ((!this.getUserPassword().isEmpty()) && (Objects.equals(this.getUserPassword(), this.getUserPasswordRepeat())));
926         }
927
928         @Override
929         public boolean isUserIdEmpty () {
930                 return ((this.getUserId() == null) || (this.getUserId() == 0));
931         }
932
933         @Override
934         public boolean isUserNameRegistered (final User user) {
935                 return ((this.userNameCache instanceof List) && (this.userNameCache.containsKey(user.getUserId())));
936         }
937
938         @Override
939         public boolean isUserNameRequired () {
940                 // Get context parameter
941                 String contextParameter = FacesContext.getCurrentInstance().getExternalContext().getInitParameter("is_user_login_require_user_name"); //NOI18N
942
943                 // Is it set?
944                 boolean isRequired = ((contextParameter instanceof String) && (contextParameter.toLowerCase().equals("true"))); //NOI18N
945
946                 // Return value
947                 return isRequired;
948         }
949
950         @Override
951         public User lookupUserByEmailAddress (final String emailAddress) throws UserEmailAddressNotFoundException {
952                 // Parameter must be valid
953                 if (null == emailAddress) {
954                         // Throw NPE
955                         throw new NullPointerException("emailAddress is null"); //NOI18N
956                 } else if (emailAddress.isEmpty()) {
957                         // Not valid
958                         throw new IllegalArgumentException("emailAddress is empty"); //NOI18N
959                 }
960
961                 // Init variable
962                 User user = null;
963
964                 // Try to lookup it in visible user list
965                 for (final Iterator<Cache.Entry<Long, User>> iterator = this.userCache.iterator(); iterator.hasNext();) {
966                         // Get next user
967                         Cache.Entry<Long, User> next = iterator.next();
968
969                         // Contact should be set
970                         if (next.getValue().getUserContact() == null) {
971                                 // Contact is null
972                                 throw new NullPointerException(MessageFormat.format("next.userContact is null for user id {0}", next.getKey())); //NOI18N
973                         } else if (next.getValue().getUserContact().getContactEmailAddress() == null) {
974                                 // Email address should be set
975                                 throw new NullPointerException(MessageFormat.format("next.userContact.contactEmailAddress is null for user id {0}", next.getKey())); //NOI18N
976                         }
977
978                         // Is the email address found?
979                         if (Objects.equals(next.getValue().getUserContact().getContactEmailAddress(), emailAddress)) {
980                                 // Copy to other variable
981                                 user = next.getValue();
982                                 break;
983                         }
984                 }
985
986                 // Is it still null?
987                 if (null == user) {
988                         // Not visible for the current user
989                         throw new UserEmailAddressNotFoundException(emailAddress);
990                 }
991
992                 // Return it
993                 return user;
994         }
995
996         @Override
997         public User lookupUserById (final Long userId) throws UserNotFoundException {
998                 // Parameter must be valid
999                 if (null == userId) {
1000                         // Throw NPE
1001                         throw new NullPointerException("userId is null"); //NOI18N
1002                 } else if (userId < 1) {
1003                         // Not valid
1004                         throw new IllegalArgumentException(MessageFormat.format("userId={0} is not valid.", userId)); //NOI18N
1005                 }
1006
1007                 // Init variable
1008                 User user = null;
1009
1010                 // Try to lookup it in visible user list
1011                 for (final Iterator<Cache.Entry<Long, User>> iterator = this.userCache.iterator(); iterator.hasNext();) {
1012                         // Get next user
1013                         Cache.Entry<Long, User> next = iterator.next();
1014
1015                         // Is the user id found?
1016                         if (Objects.equals(next.getKey(), userId)) {
1017                                 // Copy to other variable
1018                                 user = next.getValue();
1019                                 break;
1020                         }
1021                 }
1022
1023                 // Is it still null?
1024                 if (null == user) {
1025                         // Not visible for the current user
1026                         throw new UserNotFoundException(userId);
1027                 }
1028
1029                 // Return it
1030                 return user;
1031         }
1032
1033         /**
1034          * Adds user's name to bean's internal list. It also updates the public user
1035          * list if the user has decided to have a public account,
1036          * <p>
1037          * @param user User instance
1038          */
1039         private void addUserName (final User user) {
1040                 // Make sure the entry is not added yet
1041                 if (this.userNameCache.containsKey(user.getUserId())) {
1042                         // Abort here
1043                         throw new IllegalArgumentException(MessageFormat.format("User name {0} already added.", user.getUserName())); //NOI18N
1044                 }
1045
1046                 // Add user name
1047                 this.userNameCache.put(user.getUserId(), user.getUserName());
1048         }
1049
1050         /**
1051          * Clears this bean
1052          */
1053         private void clear () {
1054                 // Clear all data
1055                 // - personal data
1056                 this.setUserId(null);
1057                 this.setUserProfileMode(null);
1058
1059                 // - other data
1060                 this.clearUserName();
1061                 this.clearUserPasswords();
1062                 this.setLocale(null);
1063         }
1064
1065         /**
1066          * Clears user name
1067          */
1068         private void clearUserName () {
1069                 // Clear it
1070                 this.setUserName(null);
1071         }
1072
1073         /**
1074          * Clears both user passwords
1075          */
1076         private void clearUserPasswords () {
1077                 // Clear both
1078                 this.setUserPassword(null);
1079                 this.setUserPasswordRepeat(null);
1080         }
1081
1082         /**
1083          * Copies given user into the controller
1084          * <p>
1085          * @param user User instance
1086          */
1087         private void copyUser (final User user) {
1088                 // Make sure the instance is valid
1089                 if (null == user) {
1090                         // Throw NPE
1091                         throw new NullPointerException("user is null"); //NOI18N
1092                 } else if (user.getUserContact() == null) {
1093                         // Throw again ...
1094                         throw new NullPointerException("user.userContact is null"); //NOI18N
1095                 }
1096
1097                 // Copy all fields:
1098                 // - base data
1099                 this.setUserId(user.getUserId());
1100                 this.setUserProfileMode(user.getUserProfileMode());
1101         }
1102
1103         /**
1104          * Getter for locale instance
1105          * <p>
1106          * @return Locale instance
1107          */
1108         private Locale getLocale () {
1109                 return this.locale;
1110         }
1111
1112         /**
1113          * Setter for locale instance
1114          * <p>
1115          * @param locale Locale instance
1116          */
1117         private void setLocale (final Locale locale) {
1118                 this.locale = locale;
1119         }
1120
1121         /**
1122          * Removes user from all lists
1123          * <p>
1124          * @param user User to remove
1125          */
1126         private void removeFromList (final User user) {
1127                 // The user should be valid
1128                 if (null == user) {
1129                         // Throw NPE
1130                         throw new NullPointerException("user is null"); //NOI18N
1131                 } else if (user.getUserId() == null) {
1132                         // ... again NPE
1133                         throw new NullPointerException("user.userId is null"); //NOI18N
1134                 } else if (user.getUserId() < 1) {
1135                         // Invalid id
1136                         throw new IllegalArgumentException(MessageFormat.format("user.userId={0} is invalid", user.getUserId())); //NOI18N
1137                 }
1138
1139                 // Remove it from lists
1140                 this.userCache.remove(user.getUserId());
1141
1142                 // Remove name from list
1143                 this.userNameCache.remove(user.getUserId());
1144         }
1145
1146         /**
1147          * Updates list with given user instance
1148          * <p>
1149          * @param user User instance
1150          */
1151         private void updateList (final User user) {
1152                 // The user should be valid
1153                 if (null == user) {
1154                         // Throw NPE
1155                         throw new NullPointerException("user is null"); //NOI18N
1156                 } else if (user.getUserId() == null) {
1157                         // ... again NPE
1158                         throw new NullPointerException("user.userId is null"); //NOI18N
1159                 } else if (user.getUserId() < 1) {
1160                         // Invalid id
1161                         throw new IllegalArgumentException(MessageFormat.format("user.userId={0} is invalid", user.getUserId())); //NOI18N
1162                 } else if (user.getUserContact() == null) {
1163                         // Throw again ...
1164                         throw new NullPointerException("user.userContact is null"); //NOI18N
1165                 } else if (user.getUserContact().getContactId() == null) {
1166                         // Throw again ...
1167                         throw new NullPointerException("user.userContact.contactId is null"); //NOI18N
1168                 } else if (user.getUserContact().getContactId() < 1) {
1169                         // Throw again ...
1170                         throw new NullPointerException(MessageFormat.format("user.userContact.contactId={0} is invalid.", user.getUserContact().getContactId())); //NOI18N
1171                 }
1172
1173                 // Add/update user
1174                 this.userCache.put(user.getUserId(), user);
1175         }
1176
1177 }