--- /dev/null
+/*******************************************************************************
+ * Copyright � Igor Barma, Alexandre Desoubeaux, Christian Martel, Eric Brun, Mathieu Amblard, Gwenael Gevet, Pierre Guillot, 2012
+ * Copyright Alexandre Desoubeaux, Christian Martel, Cedric Lecarpentier, Alexandre Lefevre, Marc Salvat 2014-2016
+ * Copyright Alexandre Desoubeaux, Christian Martel, Cedric Lecarpentier, Marc Salvat, Marc Suarez, Harifetra Ramamonjy 2017
+ *
+ * This file is part of the work and learning management system Pentila Nero.
+ *
+ * Pentila Nero is free software. You can redistribute it and/or modify since
+ * you respect the terms of either (at least one of the both license) :
+ * - under the terms of the GNU Affero General Public License as
+ * published by the Free Software Foundation, either version 3 of the
+ * License, or (at your option) any later version.
+ * - the CeCILL-C as published by CeCILL-C; either version 1 of the
+ * License, or any later version
+ * - the GNU Lesser General Public License as published by the
+ * Free Software Foundation, either version 3 of the license,
+ * or (at your option) any later version.
+ *
+ * There are special exceptions to the terms and conditions of the
+ * licenses as they are applied to this software. View the full text of
+ * the exception in file LICENSE-PROJECT.txt in the directory of this software
+ * distribution.
+ *
+ * Pentila Nero is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * Licenses for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * and the CeCILL-C and the GNU Lesser General Public License along with
+ * Pentila Nero. If not, see :
+ * <http://www.gnu.org/licenses/> and
+ * <http://www.cecill.info/licences.fr.html>.
+ ******************************************************************************/
+package com.pentila.entSavoie.actions;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+
+import javax.naming.Binding;
+import javax.naming.directory.Attributes;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+import com.liferay.portal.kernel.events.Action;
+import com.liferay.portal.kernel.events.ActionException;
+import com.liferay.portal.kernel.log.Log;
+import com.liferay.portal.kernel.log.LogFactoryUtil;
+import com.liferay.portal.kernel.search.Indexer;
+import com.liferay.portal.kernel.search.IndexerRegistryUtil;
+import com.liferay.portal.kernel.search.SearchException;
+import com.liferay.portal.kernel.util.StringPool;
+import com.liferay.portal.model.Layout;
+import com.liferay.portal.model.Organization;
+import com.liferay.portal.model.User;
+import com.liferay.portal.model.UserGroup;
+import com.liferay.portal.security.ldap.PortalLDAPUtil;
+import com.liferay.portal.security.permission.PermissionCacheUtil;
+import com.liferay.portal.service.LayoutLocalServiceUtil;
+import com.liferay.portal.service.UserGroupLocalServiceUtil;
+import com.liferay.portal.service.UserLocalServiceUtil;
+import com.liferay.portal.util.PortalUtil;
+import com.pentila.entSavoie.applicationManager.ApplicationManagerUtils;
+import com.pentila.entSavoie.communityInfos.service.GroupInfosLocalServiceUtil;
+import com.pentila.entSavoie.communityInfos.service.GroupUtilsLocalServiceUtil;
+import com.pentila.entSavoie.synchroLdap.impl.SynchronizationManager;
+import com.pentila.entSavoie.utils.ENTMainUtilsLocalServiceUtil;
+import com.pentila.entSavoie.utils.ENTOrganizationsUtil;
+import com.pentila.entSavoie.utils.GroupCacheUtil;
+import com.pentila.entSavoie.utils.PortletConstant;
+import com.pentila.entSavoie.utils.XitiUtil;
+
+/**
+ * @author Tardy Camille - Barma Igor
+ *
+ * Cette action vas permettre de
+ * <ol>
+ * <li>Inscrire l'utilisateur dans l'UserGroup correspondant. Cela aura pour consequence la
+ * génération des pages dans l'espace utilisateur</li>
+ * </ol>
+ *
+ */
+public class UpdateGroupsOnLoginAction extends Action{
+
+ @Override
+ public void run(HttpServletRequest request, HttpServletResponse response)
+ throws ActionException {
+ try {
+ //Utilisateur venant de se loguer
+ final User currUser = PortalUtil.getUser(request);
+ final long[] userIds = {currUser.getUserId()};
+
+ //on verifie que le user possede "cartable de savoie" (cad si il y abien eu synchro avec le LDAP)
+ Organization cartableSavoie = ENTOrganizationsUtil.getOrCreateRootOrg(currUser.getCompanyId());
+
+ //si pas dedans : synchroniser ce user avec le LDAP
+ if (!UserLocalServiceUtil.hasOrganizationUser(cartableSavoie.getOrganizationId(), currUser.getUserId())){
+
+ try {
+ Binding binding = PortalLDAPUtil.getUser(currUser.getCompanyId(), currUser.getScreenName());
+ String userDN = PortalLDAPUtil.getNameInNamespace(currUser.getCompanyId(),binding);
+ Attributes attrs = PortalLDAPUtil.getUserAttributes(currUser.getCompanyId(), userDN);
+
+ //on import le user
+ SynchronizationManager.synchronizeUser(currUser.getCompanyId(), attrs, StringPool.BLANK, false);
+ } catch (Exception exc) {
+
+ }
+
+ //envoie d'un mail de notification (synchro partielle)
+// String sbjt = "Bienvenue dans l'environnement numérique des collèges de " + ENTMainUtilsLocalServiceUtil.getENTOrgRootDepartment(currUser.getCompanyId()) + ".";
+// String content = "Bienvenue dans l'environnement numérique des collèges de " + ENTMainUtilsLocalServiceUtil.getENTOrgRootDepartment(currUser.getCompanyId()) + ",<br><br>" +
+// "Votre compte vient d'être activé partiellement.<br>" +
+// "Attention, vous ne pouvez pas encore avoir accès à vos classes! " +
+// "Pour cela, vous devez attendre une synchronisation avec l'annuaire SCONET qui s'effectuera sous 24 heures." +
+// "Vous pouvez cependant commencer à utiliser l'ensemble des services mis à votre disposition. <br>" ;
+// Set<Long> receivers = new HashSet<Long>();
+// receivers.add(currUser.getUserId());
+// IMUtils.sendAwarenessMessage(currUser.getGroup().getGroupId(), receivers, sbjt, content, JSONFactoryUtil.createJSONArray());
+ }
+
+ List<UserGroup> allAppUserGrps = ApplicationManagerUtils.getAllApplicationGroups(currUser.getCompanyId());
+ HashSet<UserGroup> userAppGrps = ApplicationManagerUtils.getUserApplicationRoles(currUser);
+
+ // get all layout for app groups
+ List<Long> listAllAppUserGrpIds = new ArrayList<Long>();
+ for(UserGroup userGrpApp : allAppUserGrps){
+ listAllAppUserGrpIds.add(userGrpApp.getGroup().getGroupId());
+ }
+ Map<Long,List<Layout>> mapsLayoutPerGroup = GroupUtilsLocalServiceUtil.getLayoutForGroups(listAllAppUserGrpIds, true);
+
+
+ // pages privees du user
+ List<Layout> privatePages = LayoutLocalServiceUtil.getLayouts(currUser.getGroup().getGroupId(), true);
+ List<String> currentUserPagesFriendlyUrls = new ArrayList<String>();
+ for (Layout l:privatePages) {
+ currentUserPagesFriendlyUrls.add(l.getFriendlyURL());
+ }
+
+ List<String> pagesFriendlyUrls = new ArrayList<String>();
+
+ List<UserGroup> usersUserGroup = UserGroupLocalServiceUtil.getUserUserGroups(currUser.getUserId());
+
+ List<Long> usersGroupsToUnset = new ArrayList<Long>();
+ for (UserGroup userGrpApp : allAppUserGrps) {
+ //Determine si l'utilisateur dispose du role
+ final boolean hasRole = userAppGrps.contains(userGrpApp);
+
+ if (hasRole) {
+ // boolean pour checker si on doit verifier les pages
+ boolean checkUserPages = false;
+
+ // get group layout from map, init empty a array list if there no layout for the group
+ List<Layout> grpLayout = mapsLayoutPerGroup.get(userGrpApp.getGroup().getGroupId());
+ grpLayout = grpLayout != null ? grpLayout : new ArrayList<Layout>();
+
+ //Si l'utilisateur n'avais pas deja le groupe,
+ //l'ajoute afin qu'il puisse disposer des pages
+ //correspondantes.
+
+ if (!usersUserGroup.contains(userGrpApp)) {
+ try{
+ UserLocalServiceUtil.addUserGroupUsers(userGrpApp.getUserGroupId(), userIds);
+ }
+ catch(Exception exc) {
+ // la personne est semble-t-il pas dans le groupe mais elle a deja une page du meme nom!!!
+ // on supprime les pages du memes nom que celle dans le groupe et on relance avec le checkUserPages
+ // on stocke les pages privées associées au groupe
+ _log.error("Error during group setting :" + userGrpApp.getName());
+ for (Layout userL:privatePages) {
+ for (Layout l : grpLayout) {
+ if (userL.getFriendlyURL().equals(l.getFriendlyURL())) {
+ // on supprime la page du user!!!
+ LayoutLocalServiceUtil.deleteLayout(userL);
+ _log.warn("Pge delete for user: " + userL.getFriendlyURL());
+ }
+ }
+ }
+ checkUserPages = true;
+ }
+ }
+ else {
+ // la personne a deja le groupe donc on va verifier les pages
+ checkUserPages = true;
+ }
+
+ for (Layout l : grpLayout) {
+ pagesFriendlyUrls.add(l.getFriendlyURL());
+ // on va verifier que le user a bien les pages du groupes si on ne vient pas de l'inscrire!!! --> il devrait deja avoir les pages!!!
+ if (checkUserPages && !currentUserPagesFriendlyUrls.contains(l.getFriendlyURL())) {
+ // Probleme --> le user ne possede pas les pages attendues!!, il etait pourtant deja dans le groupe
+ // on supprime tout simplement la personne du grp de users
+ UserLocalServiceUtil.unsetUserGroupUsers(userGrpApp.getUserGroupId(), userIds);
+ // normalement le grp ne possede que une page <--> application donc on sait que c'est celle-ci et on re-inscrit le user
+ // sinon ben le user aura ses pages au prochain login!
+ if (grpLayout.size()==1) {
+ UserLocalServiceUtil.addUserGroupUsers(userGrpApp.getUserGroupId(), userIds);
+ }
+ }
+ }
+ } else {
+ //S'assure que la personne n'est plus dans le groupe
+ //applicatif
+ usersGroupsToUnset.add(userGrpApp.getUserGroupId());
+ }
+ }
+ this.unsetUserGroupsForAUser(usersGroupsToUnset,currUser.getUserId());
+ // On supprime les pages que l'utilisateur ne doit pas avoir!
+ final List<Layout> userPrivateLayouts = LayoutLocalServiceUtil.getLayouts(currUser.getGroup().getGroupId(), true);
+ int nbUserPages = userPrivateLayouts.size();
+
+ for (Layout l : userPrivateLayouts) {
+ if (!pagesFriendlyUrls.contains(l.getFriendlyURL())) {
+ //Suppression de la pages
+ LayoutLocalServiceUtil.deleteLayout(l);
+ }
+ else {
+ // on verifie sa place - En fait l'affichage de la premiere page
+ // Define portlet display priority for landing page
+ if (l.isTypePortlet()) {
+ int priority = nbUserPages+1;
+
+ String defaultPage = ENTMainUtilsLocalServiceUtil.getLoginDefaultPageLanding(currUser.getCompanyId());
+ if (l.getFriendlyURL().equals(defaultPage)) {
+ priority = 0;
+ }
+ else if (l.getTypeSettings().contains(PortletConstant.DASHBOARD_PORTLET_ID)) {
+ priority = 1;
+ }
+ else if (l.getTypeSettings().contains(PortletConstant.CARTABLE_PORTLET_ID)) {
+ priority = 2;
+ }
+ else if (l.getTypeSettings().contains(PortletConstant.CASIER_CARTABLE_PORTLET_ID)) {
+ priority = 3;
+ }
+ else if (l.getTypeSettings().contains(PortletConstant.ACTUALITES_PORTLET_ID)) {
+ priority = 4;
+ }
+
+ l.setPriority(priority);
+ LayoutLocalServiceUtil.updateLayout(l, true);
+ }
+ }
+ }
+
+ if(ENTMainUtilsLocalServiceUtil.getXitiEnable(currUser.getCompanyId())){
+ //On envoie une requete xiti
+ XitiUtil.sendXitiRequest(XitiUtil.getEtab(currUser), XitiUtil.EMPTY_LIB_SERVICE, currUser.getUserId(), XitiUtil.EMPTY_INTEGER_ID, XitiUtil.getRole(currUser), currUser.getCompanyId());
+ }
+
+ // Build group cache
+ GroupCacheUtil.getUserGroups(currUser);
+ _log.info("Built group cache for user "+currUser.getFullName());
+
+ } catch (Exception e) {
+ if (_log.isErrorEnabled()) {
+ _log.error(e);
+ }
+ throw new ActionException(e);
+ }
+ }
+
+ /**
+ * remove some user group for a user in table user_userGroups
+ * @param listUserGroupsId the id list of userGroup to delete
+ * @param userId the id of user it will delete the user group
+ * @throws SearchException
+ */
+ private void unsetUserGroupsForAUser (List<Long> listUserGroupsId, long userId) throws SearchException {
+ GroupInfosLocalServiceUtil.unsetUserGroupsForAUser(listUserGroupsId, userId);
+ Indexer indexer = IndexerRegistryUtil.nullSafeGetIndexer(User.class);
+
+ indexer.reindex(userId);
+
+ PermissionCacheUtil.clearCache();
+ }
+
+ private Log _log = LogFactoryUtil.getLog(this.getClass());
+}