Fixes issue 24120: Widgets embedded in tabs are supported again
authorAugusto Mauch <augusto.mauch@openbravo.com>
Tue, 18 Jun 2013 19:54:08 +0200
changeset 20522 d1cd72b22ae1
parent 20521 1d28a3f5de04
child 20523 ea147caea984
Fixes issue 24120: Widgets embedded in tabs are supported again

In this changeset [1] some logic was added to restrict the access to the widgets. One of the checks consisted in throwing an exception if the widget class did not have any widget instance class associated. This makes sense for workspace widgets, but widgets embedded in tabs do not have widget instance classes.

Now, this check is only done if the widget is not embedded in a window accessible by the user.


[1] https://code.openbravo.com/erp/devel/pi/rev/08d5a13b722bbc496c640a976d5bb319a1db44bc
modules/org.openbravo.client.querylist/src/org/openbravo/client/querylist/QueryListDataSource.java
--- a/modules/org.openbravo.client.querylist/src/org/openbravo/client/querylist/QueryListDataSource.java	Thu Jun 13 18:13:37 2013 +0200
+++ b/modules/org.openbravo.client.querylist/src/org/openbravo/client/querylist/QueryListDataSource.java	Tue Jun 18 19:54:08 2013 +0200
@@ -39,6 +39,7 @@
 import org.codehaus.jettison.json.JSONException;
 import org.codehaus.jettison.json.JSONObject;
 import org.hibernate.Query;
+import org.hibernate.criterion.Restrictions;
 import org.openbravo.base.exception.OBException;
 import org.openbravo.base.exception.OBSecurityException;
 import org.openbravo.base.model.ModelProvider;
@@ -58,10 +59,16 @@
 import org.openbravo.client.kernel.reference.YesNoUIDefinition;
 import org.openbravo.client.myob.WidgetClass;
 import org.openbravo.client.myob.WidgetInstance;
+import org.openbravo.client.myob.WidgetReference;
 import org.openbravo.dal.core.OBContext;
+import org.openbravo.dal.service.OBCriteria;
 import org.openbravo.dal.service.OBDal;
 import org.openbravo.erpCommon.utility.OBMessageUtils;
+import org.openbravo.model.ad.access.WindowAccess;
+import org.openbravo.model.ad.datamodel.Column;
 import org.openbravo.model.ad.domain.Reference;
+import org.openbravo.model.ad.ui.Field;
+import org.openbravo.model.ad.ui.Window;
 import org.openbravo.portal.PortalAccessible;
 import org.openbravo.service.datasource.DataSourceProperty;
 import org.openbravo.service.datasource.ReadOnlyDataSourceService;
@@ -104,7 +111,13 @@
       // Check security: continue only if the widget instance is visible for current user/role
       WidgetInstance wi = OBDal.getInstance().get(WidgetInstance.class,
           parameters.get("widgetInstanceId"));
-      if (wi == null || wi.getWidgetClass().getId() != widgetClass.getId()) {
+
+      boolean accessibleWidgetInForm = false;
+      if (wi == null) {
+        accessibleWidgetInForm = isAccessibleWidgetInForm(widgetClass);
+      }
+      if (!accessibleWidgetInForm
+          && (wi == null || wi.getWidgetClass().getId() != widgetClass.getId())) {
         // weird stuff: widget class doesn't match widget instance's class, most probably URL is
         // not generated by UI, but user is typing it
         log.error("User " + OBContext.getOBContext().getUser() + " with role "
@@ -114,11 +127,11 @@
             new String[] { widgetClass.getWidgetTitle() }));
       }
 
-      if (OBContext.getOBContext() != null
-          && ((wi.getVisibleAtUser() != null && !wi.getVisibleAtUser().getId()
-              .equals(OBContext.getOBContext().getUser().getId())))
-          || (wi.getVisibleAtRole() != null && !wi.getVisibleAtRole().getId()
-              .equals(OBContext.getOBContext().getRole().getId()))) {
+      if (!accessibleWidgetInForm
+          && (OBContext.getOBContext() != null
+              && ((wi.getVisibleAtUser() != null && !wi.getVisibleAtUser().getId()
+                  .equals(OBContext.getOBContext().getUser().getId()))) || (wi.getVisibleAtRole() != null && !wi
+              .getVisibleAtRole().getId().equals(OBContext.getOBContext().getRole().getId())))) {
         log.error("User " + OBContext.getOBContext().getUser() + " with role "
             + OBContext.getOBContext().getRole() + " is trying to access widget '"
             + widgetClass.getWidgetTitle() + "' which is not granted");
@@ -243,6 +256,38 @@
     }
   }
 
+  // Checks if the widget is embedded in a tab accessible by the user
+  private boolean isAccessibleWidgetInForm(WidgetClass widgetClass) {
+    OBCriteria<WidgetReference> widgetInFormCriteria = OBDal.getInstance().createCriteria(
+        WidgetReference.class);
+    widgetInFormCriteria.add(Restrictions.eq(WidgetReference.PROPERTY_WIDGETCLASS, widgetClass));
+    List<Window> windowList = new ArrayList<Window>();
+    List<WidgetReference> widgetInFormList = widgetInFormCriteria.list();
+    for (WidgetReference widgetInForm : widgetInFormList) {
+      List<Column> columnList = widgetInForm.getReference().getADColumnReferenceSearchKeyList();
+      for (Column column : columnList) {
+        List<Field> fieldList = column.getADFieldList();
+        for (Field field : fieldList) {
+          windowList.add(field.getTab().getWindow());
+        }
+      }
+    }
+
+    if (windowList.isEmpty()) {
+      // The widget is not embedded in any window
+      return false;
+    } else {
+      OBCriteria<WindowAccess> accessibleWindowCriteria = OBDal.getInstance().createCriteria(
+          WindowAccess.class);
+      accessibleWindowCriteria.add(Restrictions.eq(WindowAccess.PROPERTY_ROLE, OBContext
+          .getOBContext().getRole()));
+      accessibleWindowCriteria.add(Restrictions.in(WindowAccess.PROPERTY_WINDOW, windowList));
+      int count = accessibleWindowCriteria.count();
+      // If the widget is embedded in at least one window accessible by the user, return true
+      return (count > 0);
+    }
+  }
+
   // Converts and object from String to Date
   private Date convertToDate(String value) {
     DateDomainType domainType = new DateDomainType();