diff -r f406f8d39b79 src/org/openbravo/retail/posterminal/UserRoleEventHandler.java
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/org/openbravo/retail/posterminal/UserRoleEventHandler.java	Thu Mar 05 19:16:01 2020 +0100
@@ -0,0 +1,145 @@
+/*
+ ************************************************************************************
+ * Copyright (C) 2018-2019 Openbravo S.L.U.
+ * Licensed under the Openbravo Commercial License version 1.0
+ * You may obtain a copy of the License at http://www.openbravo.com/legal/obcl.html
+ * or in the legal folder of this module distribution.
+ ************************************************************************************
+ */
+
+package org.openbravo.retail.posterminal;
+
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import javax.enterprise.event.Observes;
+
+import org.apache.log4j.Logger;
+import org.hibernate.Transaction;
+import org.hibernate.criterion.Restrictions;
+import org.openbravo.base.model.Entity;
+import org.openbravo.base.model.ModelProvider;
+import org.openbravo.base.provider.OBProvider;
+import org.openbravo.client.kernel.event.EntityNewEvent;
+import org.openbravo.client.kernel.event.EntityPersistenceEvent;
+import org.openbravo.client.kernel.event.EntityPersistenceEventObserver;
+import org.openbravo.client.kernel.event.EntityUpdateEvent;
+import org.openbravo.client.kernel.event.TransactionBeginEvent;
+import org.openbravo.client.kernel.event.TransactionCompletedEvent;
+import org.openbravo.dal.core.SessionHandler;
+import org.openbravo.dal.service.OBCriteria;
+import org.openbravo.dal.service.OBDal;
+import org.openbravo.model.ad.access.Role;
+import org.openbravo.model.ad.access.User;
+import org.openbravo.model.ad.access.UserRoles;
+
+public class UserRoleEventHandler extends EntityPersistenceEventObserver {
+
+  private static Entity[] entities = {
+      ModelProvider.getInstance().getEntity(UserRoles.ENTITY_NAME) };
+  protected Logger logger = Logger.getLogger(this.getClass());
+
+  private static ThreadLocal<Map<Transaction, Map<String, Set<Role>>>> user_role = new ThreadLocal<>();
+  private static ThreadLocal<Transaction> currentTransaction = new ThreadLocal<>();
+
+  @Override
+  protected Entity[] getObservedEntities() {
+    return entities;
+  }
+
+  public void onTransactionBegin(@Observes final TransactionBeginEvent event) {
+    currentTransaction.set(event.getTransaction());
+  }
+
+  public void onUpdate(@Observes final EntityUpdateEvent event) {
+    if (!isValidEvent(event)) {
+      return;
+    }
+    registerChanges(event);
+  }
+
+  public void onSave(@Observes final EntityNewEvent event) {
+    if (!isValidEvent(event)) {
+      return;
+    }
+    registerChanges(event);
+  }
+
+  public void onTransactionCompleted(@Observes final TransactionCompletedEvent event) {
+    try {
+      final Transaction tx = event.getTransaction();
+      if (user_role.get() != null) {
+        if (!SessionHandler.getInstance().isCurrentTransactionActive()) {
+          SessionHandler.getInstance().beginNewTransaction();
+        }
+        final Map<String, Set<Role>> urMap = user_role.get().get(tx);
+        for (final Map.Entry<String, Set<Role>> ur : urMap.entrySet()) {
+          for (final Role role : ur.getValue()) {
+            savePosTerminalAccess(OBDal.getInstance().getProxy(User.class, ur.getKey()), role);
+          }
+        }
+        OBDal.getInstance().flush();
+      }
+    } catch (final Exception e) {
+      logger.error(e.getMessage(), e);
+    }
+  }
+
+  private void registerChanges(final EntityPersistenceEvent event) {
+    final Transaction tx = currentTransaction.get();
+    if (user_role.get() == null) {
+      final Map<Transaction, Map<String, Set<Role>>> new_user_role = new HashMap<>();
+      new_user_role.put(tx, new HashMap<>());
+      user_role.set(new_user_role);
+    }
+    final Map<String, Set<Role>> txMap = user_role.get().get(tx);
+
+    final Entity userRolesEntity = ModelProvider.getInstance().getEntity(UserRoles.ENTITY_NAME);
+    final User user = (User) event
+        .getCurrentState(userRolesEntity.getProperty(UserRoles.PROPERTY_USERCONTACT));
+    final UserRoles urs = (UserRoles) event.getTargetInstance();
+    final Role role = urs.getRole();
+
+    if (txMap.containsKey(user.getId())) {
+      txMap.get(user.getId()).add(role);
+    } else {
+      final Set<Role> newRole = new HashSet<>();
+      txMap.put(user.getId(), newRole);
+    }
+  }
+
+  private void savePosTerminalAccess(final User user, final Role role) {
+    final boolean isTemplate = role.isTemplate();
+
+    if (!isTemplate) {
+      final boolean isOK = true;
+    }
+  }
+
+  private void addPosTerminalAccess(final User user, final TerminalType terminalType) {
+    final List<OBPOSApplications> posTerminalList = terminalType.getOBPOSApplicationsList();
+    TerminalAccess posTerminalAccess = null;
+    for (final OBPOSApplications pos : posTerminalList) {
+      if (!existPosTerminalAccess(user, pos)) {
+        posTerminalAccess = OBProvider.getInstance().get(TerminalAccess.class);
+        posTerminalAccess.setPOSTerminal(pos);
+        posTerminalAccess.setUserContact(user);
+        posTerminalAccess.setOrganization(pos.getOrganization());
+        OBDal.getInstance().save(posTerminalAccess);
+      }
+    }
+  }
+
+  private boolean existPosTerminalAccess(final User user, final OBPOSApplications pos) {
+    final OBCriteria<TerminalAccess> terminalAccessCriteria = OBDal.getInstance()
+        .createCriteria(TerminalAccess.class);
+    terminalAccessCriteria.add(Restrictions.eq(TerminalAccess.PROPERTY_POSTERMINAL, pos));
+    terminalAccessCriteria.add(Restrictions.eq(TerminalAccess.PROPERTY_USERCONTACT, user));
+    terminalAccessCriteria.setMaxResults(1);
+
+    return terminalAccessCriteria.uniqueResult() != null;
+  }
+}
