You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@syncope.apache.org by il...@apache.org on 2018/07/12 09:34:32 UTC

syncope git commit: [SYNCOPE-1336] Pagination and sorting controls added

Repository: syncope
Updated Branches:
  refs/heads/2_0_X 866932334 -> 6db41512e


[SYNCOPE-1336] Pagination and sorting controls added


Project: http://git-wip-us.apache.org/repos/asf/syncope/repo
Commit: http://git-wip-us.apache.org/repos/asf/syncope/commit/6db41512
Tree: http://git-wip-us.apache.org/repos/asf/syncope/tree/6db41512
Diff: http://git-wip-us.apache.org/repos/asf/syncope/diff/6db41512

Branch: refs/heads/2_0_X
Commit: 6db41512edd80306347a2d8e79730c37bf76d196
Parents: 8669323
Author: Francesco Chicchiriccò <il...@apache.org>
Authored: Thu Jul 12 11:34:19 2018 +0200
Committer: Francesco Chicchiriccò <il...@apache.org>
Committed: Thu Jul 12 11:34:24 2018 +0200

----------------------------------------------------------------------
 .../approvals/ApprovalDirectoryPanel.java       |  19 ++--
 .../console/commons/TaskDataProvider.java       |   4 -
 .../console/rest/UserWorkflowRestClient.java    |  14 ++-
 .../client/console/widgets/AlertWidget.java     |  34 ++-----
 .../client/console/widgets/ApprovalsWidget.java | 101 +++----------------
 .../client/console/widgets/AlertWidget.html     |   6 +-
 .../widgets/ApprovalsWidget$InnerPanel.html     |  27 -----
 .../common/rest/api/beans/TaskQuery.java        |   1 -
 .../rest/api/beans/WorkflowFormQuery.java       |  32 ++++++
 .../rest/api/service/UserWorkflowService.java   |   6 +-
 .../syncope/core/logic/UserWorkflowLogic.java   |   9 +-
 .../cxf/service/UserWorkflowServiceImpl.java    |  11 +-
 .../activiti/ActivitiUserWorkflowAdapter.java   |  79 ++++++++++-----
 .../core/workflow/api/WorkflowAdapter.java      |  13 ++-
 .../flowable/FlowableUserWorkflowAdapter.java   |  79 ++++++++++-----
 .../java/DefaultAnyObjectWorkflowAdapter.java   |   8 +-
 .../java/DefaultGroupWorkflowAdapter.java       |   8 +-
 .../java/DefaultUserWorkflowAdapter.java        |   7 +-
 .../syncope/fit/core/SchedTaskITCase.java       |   7 +-
 .../syncope/fit/core/UserWorkflowITCase.java    |  44 ++++----
 20 files changed, 264 insertions(+), 245 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/client/console/src/main/java/org/apache/syncope/client/console/approvals/ApprovalDirectoryPanel.java
----------------------------------------------------------------------
diff --git a/client/console/src/main/java/org/apache/syncope/client/console/approvals/ApprovalDirectoryPanel.java b/client/console/src/main/java/org/apache/syncope/client/console/approvals/ApprovalDirectoryPanel.java
index 72d2916..f6bd095 100644
--- a/client/console/src/main/java/org/apache/syncope/client/console/approvals/ApprovalDirectoryPanel.java
+++ b/client/console/src/main/java/org/apache/syncope/client/console/approvals/ApprovalDirectoryPanel.java
@@ -29,10 +29,10 @@ import org.apache.commons.lang3.StringUtils;
 import org.apache.syncope.client.console.SyncopeConsoleSession;
 import org.apache.syncope.client.console.commons.Constants;
 import org.apache.syncope.client.console.commons.DirectoryDataProvider;
-import org.apache.syncope.client.console.commons.SortableDataProviderComparator;
 import org.apache.syncope.client.console.panels.DirectoryPanel;
 import org.apache.syncope.client.console.rest.UserWorkflowRestClient;
 import org.apache.syncope.client.console.approvals.ApprovalDirectoryPanel.ApprovalProvider;
+import org.apache.syncope.client.console.commons.SortableDataProviderComparator;
 import org.apache.syncope.client.console.layout.FormLayoutInfoUtils;
 import org.apache.syncope.client.console.layout.UserFormLayoutInfo;
 import org.apache.syncope.client.console.pages.BasePage;
@@ -119,14 +119,15 @@ public class ApprovalDirectoryPanel
         columns.add(new PropertyColumn<WorkflowFormTO, String>(
                 new ResourceModel("taskId"), "taskId", "taskId"));
         columns.add(new PropertyColumn<WorkflowFormTO, String>(
-                new ResourceModel("key"), "key", "key"));
+                new ResourceModel("key"), "key"));
         columns.add(new PropertyColumn<WorkflowFormTO, String>(
-                new ResourceModel("username"), "username", "username"));
+                new ResourceModel("username"), "username"));
         columns.add(new DatePropertyColumn<WorkflowFormTO>(
                 new ResourceModel("createTime"), "createTime", "createTime"));
         columns.add(new DatePropertyColumn<WorkflowFormTO>(
                 new ResourceModel("dueDate"), "dueDate", "dueDate"));
-        columns.add(new PropertyColumn<WorkflowFormTO, String>(new ResourceModel("owner"), "owner", "owner"));
+        columns.add(new PropertyColumn<WorkflowFormTO, String>(
+                new ResourceModel("owner"), "owner", "owner"));
 
         return columns;
     }
@@ -262,20 +263,20 @@ public class ApprovalDirectoryPanel
 
         public ApprovalProvider(final int paginatorRows) {
             super(paginatorRows);
+
             setSort("createTime", SortOrder.ASCENDING);
-            this.comparator = new SortableDataProviderComparator<>(this);
+            comparator = new SortableDataProviderComparator<>(this);
         }
 
         @Override
         public Iterator<WorkflowFormTO> iterator(final long first, final long count) {
-            final List<WorkflowFormTO> list = restClient.getForms();
-            Collections.sort(list, comparator);
-            return list.subList((int) first, (int) first + (int) count).iterator();
+            int page = ((int) first / paginatorRows);
+            return restClient.getForms((page < 0 ? 0 : page) + 1, paginatorRows, getSort()).iterator();
         }
 
         @Override
         public long size() {
-            return restClient.getForms().size();
+            return restClient.countForms();
         }
 
         @Override

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/client/console/src/main/java/org/apache/syncope/client/console/commons/TaskDataProvider.java
----------------------------------------------------------------------
diff --git a/client/console/src/main/java/org/apache/syncope/client/console/commons/TaskDataProvider.java b/client/console/src/main/java/org/apache/syncope/client/console/commons/TaskDataProvider.java
index 50f6fe7..b68ab42 100644
--- a/client/console/src/main/java/org/apache/syncope/client/console/commons/TaskDataProvider.java
+++ b/client/console/src/main/java/org/apache/syncope/client/console/commons/TaskDataProvider.java
@@ -40,10 +40,6 @@ public abstract class TaskDataProvider<T extends TaskTO> extends DirectoryDataPr
         this.taskType = taskType;
     }
 
-    public SortableDataProviderComparator<T> getComparator() {
-        return comparator;
-    }
-
     @Override
     public IModel<T> model(final T object) {
         return new CompoundPropertyModel<>(object);

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/client/console/src/main/java/org/apache/syncope/client/console/rest/UserWorkflowRestClient.java
----------------------------------------------------------------------
diff --git a/client/console/src/main/java/org/apache/syncope/client/console/rest/UserWorkflowRestClient.java b/client/console/src/main/java/org/apache/syncope/client/console/rest/UserWorkflowRestClient.java
index fc42f9b..8ccf057 100644
--- a/client/console/src/main/java/org/apache/syncope/client/console/rest/UserWorkflowRestClient.java
+++ b/client/console/src/main/java/org/apache/syncope/client/console/rest/UserWorkflowRestClient.java
@@ -21,14 +21,24 @@ package org.apache.syncope.client.console.rest;
 import java.util.List;
 import org.apache.syncope.common.lib.to.UserTO;
 import org.apache.syncope.common.lib.to.WorkflowFormTO;
+import org.apache.syncope.common.rest.api.beans.WorkflowFormQuery;
 import org.apache.syncope.common.rest.api.service.UserWorkflowService;
+import org.apache.wicket.extensions.markup.html.repeater.util.SortParam;
 
 public class UserWorkflowRestClient extends BaseRestClient {
 
     private static final long serialVersionUID = -4785231164900813921L;
 
-    public List<WorkflowFormTO> getForms() {
-        return getService(UserWorkflowService.class).getForms();
+    public int countForms() {
+        return getService(UserWorkflowService.class).
+                getForms(new WorkflowFormQuery.Builder().page(1).size(1).build()).
+                getTotalCount();
+    }
+
+    public List<WorkflowFormTO> getForms(final int page, final int size, final SortParam<String> sort) {
+        return getService(UserWorkflowService.class).
+                getForms(new WorkflowFormQuery.Builder().page(page).size(size).orderBy(toOrderBy(sort)).build()).
+                getResult();
     }
 
     public WorkflowFormTO getFormForUser(final String userKey) {

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/client/console/src/main/java/org/apache/syncope/client/console/widgets/AlertWidget.java
----------------------------------------------------------------------
diff --git a/client/console/src/main/java/org/apache/syncope/client/console/widgets/AlertWidget.java b/client/console/src/main/java/org/apache/syncope/client/console/widgets/AlertWidget.java
index ac32d17..f564ac8 100644
--- a/client/console/src/main/java/org/apache/syncope/client/console/widgets/AlertWidget.java
+++ b/client/console/src/main/java/org/apache/syncope/client/console/widgets/AlertWidget.java
@@ -25,8 +25,6 @@ import org.apache.wicket.markup.ComponentTag;
 import org.apache.wicket.markup.html.WebMarkupContainer;
 import org.apache.wicket.markup.html.basic.Label;
 import org.apache.wicket.markup.html.link.AbstractLink;
-import org.apache.wicket.markup.html.list.ListItem;
-import org.apache.wicket.markup.html.list.ListView;
 import org.apache.wicket.markup.html.panel.Panel;
 import org.apache.wicket.model.IModel;
 import org.apache.wicket.model.LoadableDetachableModel;
@@ -39,14 +37,14 @@ public abstract class AlertWidget<T extends Serializable> extends Panel {
 
     protected static final Logger LOG = LoggerFactory.getLogger(AlertWidget.class);
 
+    protected static final int MAX_SIZE = 5;
+
     protected final Label linkAlertsNumber;
 
     protected final Label headerAlertsNumber;
 
     protected final WebMarkupContainer latestAlertsList;
 
-    protected final ListView<T> latestFive;
-
     protected IModel<List<T>> latestAlerts;
 
     public AlertWidget(final String id) {
@@ -61,7 +59,7 @@ public abstract class AlertWidget<T extends Serializable> extends Panel {
 
             @Override
             protected Integer load() {
-                return AlertWidget.this.latestAlerts.getObject().size();
+                return getLatestAlertsSize();
             }
         };
 
@@ -72,7 +70,7 @@ public abstract class AlertWidget<T extends Serializable> extends Panel {
             @Override
             protected List<T> load() {
                 final List<T> latest = AlertWidget.this.latestAlerts.getObject();
-                return latest.subList(0, latest.size() < 6 ? latest.size() : 5);
+                return latest.subList(0, latest.size() <= MAX_SIZE ? latest.size() : MAX_SIZE);
             }
         };
 
@@ -98,31 +96,20 @@ public abstract class AlertWidget<T extends Serializable> extends Panel {
         headerAlertsNumber.setOutputMarkupId(true);
         add(headerAlertsNumber);
 
+        add(getEventsLink("alertsLink"));
+
         latestAlertsList = new WebMarkupContainer("latestAlertsList");
         latestAlertsList.setOutputMarkupId(true);
         add(latestAlertsList);
+    }
 
-        latestFive = new ListView<T>("latestAlerts", items) {
-
-            private static final long serialVersionUID = 4949588177564901031L;
-
-            @Override
-            protected void populateItem(final ListItem<T> item) {
-                item.add(getAlertLink("alert", item.getModelObject()).setRenderBodyOnly(true));
-            }
-        };
-        latestAlertsList.add(latestFive.setReuseItems(false).setOutputMarkupId(true));
-
-        add(getEventsLink("alertsLink"));
+    protected int getLatestAlertsSize() {
+        return latestAlerts.getObject().size();
     }
 
     protected abstract IModel<List<T>> getLatestAlerts();
 
-    protected Panel getAlertLink(final String panelid, final T alert) {
-        return new AlertLink<>(panelid, alert);
-    }
-
-    protected abstract AbstractLink getEventsLink(final String linkid);
+    protected abstract AbstractLink getEventsLink(String linkid);
 
     protected abstract Icon getIcon(String iconid);
 
@@ -135,5 +122,4 @@ public abstract class AlertWidget<T extends Serializable> extends Panel {
             add(new Label("alert", alert.toString()));
         }
     }
-
 }

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/client/console/src/main/java/org/apache/syncope/client/console/widgets/ApprovalsWidget.java
----------------------------------------------------------------------
diff --git a/client/console/src/main/java/org/apache/syncope/client/console/widgets/ApprovalsWidget.java b/client/console/src/main/java/org/apache/syncope/client/console/widgets/ApprovalsWidget.java
index cc41e84..bbbd51f 100644
--- a/client/console/src/main/java/org/apache/syncope/client/console/widgets/ApprovalsWidget.java
+++ b/client/console/src/main/java/org/apache/syncope/client/console/widgets/ApprovalsWidget.java
@@ -20,12 +20,9 @@ package org.apache.syncope.client.console.widgets;
 
 import de.agilecoders.wicket.core.markup.html.bootstrap.image.Icon;
 import de.agilecoders.wicket.extensions.markup.html.bootstrap.icon.FontAwesomeIconTypeBuilder;
-import java.io.Serializable;
 import java.util.ArrayList;
 import java.util.Collections;
-import java.util.Comparator;
 import java.util.List;
-import org.apache.commons.lang3.StringUtils;
 import org.apache.syncope.client.console.BookmarkablePageLinkBuilder;
 import org.apache.syncope.client.console.SyncopeConsoleSession;
 import org.apache.syncope.client.console.pages.Approvals;
@@ -35,17 +32,12 @@ import org.apache.syncope.common.lib.to.WorkflowFormTO;
 import org.apache.syncope.common.lib.types.StandardEntitlement;
 import org.apache.wicket.PageReference;
 import org.apache.wicket.ajax.AjaxRequestTarget;
-import org.apache.wicket.ajax.markup.html.AjaxLink;
 import org.apache.wicket.authroles.authorization.strategies.role.metadata.MetaDataRoleAuthorizationStrategy;
-import org.apache.wicket.markup.ComponentTag;
-import org.apache.wicket.markup.html.WebMarkupContainer;
+import org.apache.wicket.extensions.markup.html.repeater.util.SortParam;
 import org.apache.wicket.markup.html.WebPage;
-import org.apache.wicket.markup.html.basic.Label;
 import org.apache.wicket.markup.html.link.AbstractLink;
 import org.apache.wicket.markup.html.link.BookmarkablePageLink;
-import org.apache.wicket.markup.html.panel.Panel;
 import org.apache.wicket.model.IModel;
-import org.apache.wicket.model.ResourceModel;
 import org.apache.wicket.model.util.ListModel;
 import org.apache.wicket.util.time.Duration;
 
@@ -78,13 +70,13 @@ public class ApprovalsWidget extends AlertWidget<WorkflowFormTO> {
         latestAlerts.getObject().clear();
         latestAlerts.getObject().addAll(lastApprovals);
 
-        linkAlertsNumber.setDefaultModelObject(latestAlerts.getObject().size());
+        int latestAlertSize = getLatestAlertsSize();
+        linkAlertsNumber.setDefaultModelObject(latestAlertSize);
         target.add(linkAlertsNumber);
 
-        headerAlertsNumber.setDefaultModelObject(latestAlerts.getObject().size());
+        headerAlertsNumber.setDefaultModelObject(latestAlertSize);
         target.add(headerAlertsNumber);
 
-        latestFive.removeAll();
         target.add(latestAlertsList);
 
         lastApprovals.clear();
@@ -92,6 +84,14 @@ public class ApprovalsWidget extends AlertWidget<WorkflowFormTO> {
     }
 
     @Override
+    protected int getLatestAlertsSize() {
+        return SyncopeConsoleSession.get().owns(StandardEntitlement.WORKFLOW_FORM_LIST)
+                && SyncopeConsoleSession.get().owns(StandardEntitlement.WORKFLOW_FORM_READ)
+                ? restClient.countForms()
+                : 0;
+    }
+
+    @Override
     protected IModel<List<WorkflowFormTO>> getLatestAlerts() {
         return new ListModel<WorkflowFormTO>() {
 
@@ -103,8 +103,7 @@ public class ApprovalsWidget extends AlertWidget<WorkflowFormTO> {
                 if (SyncopeConsoleSession.get().owns(StandardEntitlement.WORKFLOW_FORM_LIST)
                         && SyncopeConsoleSession.get().owns(StandardEntitlement.WORKFLOW_FORM_READ)) {
 
-                    updatedApprovals = restClient.getForms();
-                    Collections.sort(updatedApprovals, new WorkflowFormComparator());
+                    updatedApprovals = restClient.getForms(1, MAX_SIZE, new SortParam<String>("createTime", true));
                 } else {
                     updatedApprovals = Collections.<WorkflowFormTO>emptyList();
                 }
@@ -115,11 +114,6 @@ public class ApprovalsWidget extends AlertWidget<WorkflowFormTO> {
     }
 
     @Override
-    protected Panel getAlertLink(final String panelid, final WorkflowFormTO event) {
-        return new ApprovalsWidget.InnerPanel(panelid, event);
-    }
-
-    @Override
     protected AbstractLink getEventsLink(final String linkid) {
         BookmarkablePageLink<Approvals> approvals = BookmarkablePageLinkBuilder.build(linkid, Approvals.class);
         MetaDataRoleAuthorizationStrategy.authorize(approvals, WebPage.ENABLE, StandardEntitlement.WORKFLOW_FORM_LIST);
@@ -131,73 +125,4 @@ public class ApprovalsWidget extends AlertWidget<WorkflowFormTO> {
         return new Icon(iconid,
                 FontAwesomeIconTypeBuilder.on(FontAwesomeIconTypeBuilder.FontAwesomeGraphic.handshake_o).build());
     }
-
-    public static final class InnerPanel extends Panel {
-
-        private static final long serialVersionUID = 3829642687027801451L;
-
-        public InnerPanel(final String id, final WorkflowFormTO alert) {
-            super(id);
-
-            final AjaxLink<String> approval = new AjaxLink<String>("approval") {
-
-                private static final long serialVersionUID = 7021195294339489084L;
-
-                @Override
-                public void onClick(final AjaxRequestTarget target) {
-                    // do nothing
-                }
-
-                @Override
-                protected void onComponentTag(final ComponentTag tag) {
-                    super.onComponentTag(tag);
-                    if (StringUtils.isNotBlank(alert.getUsername())) {
-                        tag.put("title", alert.getUsername().trim());
-                    }
-                }
-            };
-
-            add(approval);
-
-            approval.add(new Label("key", new ResourceModel(alert.getKey(), alert.getKey())).
-                    setRenderBodyOnly(true));
-
-            approval.add(new Label("owner", alert.getOwner()));
-
-            approval.add(new Label("createTime",
-                    SyncopeConsoleSession.get().getDateFormat().format(alert.getCreateTime())).
-                    setRenderBodyOnly(true));
-
-            WebMarkupContainer dueDateContainer = new WebMarkupContainer("dueDateContainer");
-            dueDateContainer.setOutputMarkupId(true);
-            approval.add(dueDateContainer);
-
-            if (alert.getDueDate() == null) {
-                dueDateContainer.add(new Label("dueDate"));
-                dueDateContainer.setVisible(false);
-            } else {
-                dueDateContainer.add(new Label("dueDate",
-                        SyncopeConsoleSession.get().getDateFormat().format(alert.getDueDate())).
-                        setRenderBodyOnly(true));
-            }
-        }
-
-    }
-
-    private static class WorkflowFormComparator implements Comparator<WorkflowFormTO>, Serializable {
-
-        private static final long serialVersionUID = 4650217602780789075L;
-
-        @Override
-        public int compare(final WorkflowFormTO o1, final WorkflowFormTO o2) {
-            if (o1 == null) {
-                return o2 == null ? 0 : 1;
-            } else if (o2 == null) {
-                return -1;
-            } else {
-                // inverse
-                return o2.getCreateTime().compareTo(o1.getCreateTime());
-            }
-        }
-    }
 }

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/client/console/src/main/resources/org/apache/syncope/client/console/widgets/AlertWidget.html
----------------------------------------------------------------------
diff --git a/client/console/src/main/resources/org/apache/syncope/client/console/widgets/AlertWidget.html b/client/console/src/main/resources/org/apache/syncope/client/console/widgets/AlertWidget.html
index e9a6433..4d75003 100644
--- a/client/console/src/main/resources/org/apache/syncope/client/console/widgets/AlertWidget.html
+++ b/client/console/src/main/resources/org/apache/syncope/client/console/widgets/AlertWidget.html
@@ -27,11 +27,7 @@ under the License.
         <wicket:message key="summary"><span wicket:id="number"/></wicket:message>
       </li>
       <li>
-        <ul wicket:id="latestAlertsList" class="menu">
-          <li class="todoitem" wicket:id="latestAlerts">
-            <span wicket:id="alert">[ALERT]</span>
-          </li>
-        </ul>
+        <span wicket:id="latestAlertsList"/>
       </li>
       <li class="footer">
         <a href="#" wicket:id="alertsLink"><wicket:message key="alerts.view.all">View all alerts</wicket:message></a>

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/client/console/src/main/resources/org/apache/syncope/client/console/widgets/ApprovalsWidget$InnerPanel.html
----------------------------------------------------------------------
diff --git a/client/console/src/main/resources/org/apache/syncope/client/console/widgets/ApprovalsWidget$InnerPanel.html b/client/console/src/main/resources/org/apache/syncope/client/console/widgets/ApprovalsWidget$InnerPanel.html
deleted file mode 100644
index 6976d65..0000000
--- a/client/console/src/main/resources/org/apache/syncope/client/console/widgets/ApprovalsWidget$InnerPanel.html
+++ /dev/null
@@ -1,27 +0,0 @@
-<!--
-Licensed to the Apache Software Foundation (ASF) under one
-or more contributor license agreements.  See the NOTICE file
-distributed with this work for additional information
-regarding copyright ownership.  The ASF licenses this file
-to you under the Apache License, Version 2.0 (the
-"License"); you may not use this file except in compliance
-with the License.  You may obtain a copy of the License at
-
-  http://www.apache.org/licenses/LICENSE-2.0
-
-Unless required by applicable law or agreed to in writing,
-software distributed under the License is distributed on an
-"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-KIND, either express or implied.  See the License for the
-specific language governing permissions and limitations
-under the License.
--->
-<html xmlns="http://www.w3.org/1999/xhtml" xmlns:wicket="http://wicket.apache.org">
-  <wicket:panel>
-    <a href="#" wicket:id="approval" style="cursor: not-allowed;">
-      <h3><small class="pull-right" wicket:id="owner"/> <p wicket:id="key"/></h3>
-      <small wicket:id="dueDateContainer" class="pull-right"><i class="fa fa-hourglass-end"></i> <p wicket:id="dueDate"/></small>
-      <small><i class="fa fa-clock-o"></i> <p wicket:id="createTime"/></small>
-    </a>
-  </wicket:panel>
-</html>
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/common/rest-api/src/main/java/org/apache/syncope/common/rest/api/beans/TaskQuery.java
----------------------------------------------------------------------
diff --git a/common/rest-api/src/main/java/org/apache/syncope/common/rest/api/beans/TaskQuery.java b/common/rest-api/src/main/java/org/apache/syncope/common/rest/api/beans/TaskQuery.java
index c96d7b2..f5cdecc 100644
--- a/common/rest-api/src/main/java/org/apache/syncope/common/rest/api/beans/TaskQuery.java
+++ b/common/rest-api/src/main/java/org/apache/syncope/common/rest/api/beans/TaskQuery.java
@@ -137,5 +137,4 @@ public class TaskQuery extends AbstractQuery {
     public void setDetails(final Boolean details) {
         this.details = details;
     }
-
 }

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/common/rest-api/src/main/java/org/apache/syncope/common/rest/api/beans/WorkflowFormQuery.java
----------------------------------------------------------------------
diff --git a/common/rest-api/src/main/java/org/apache/syncope/common/rest/api/beans/WorkflowFormQuery.java b/common/rest-api/src/main/java/org/apache/syncope/common/rest/api/beans/WorkflowFormQuery.java
new file mode 100644
index 0000000..c3454bf
--- /dev/null
+++ b/common/rest-api/src/main/java/org/apache/syncope/common/rest/api/beans/WorkflowFormQuery.java
@@ -0,0 +1,32 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.syncope.common.rest.api.beans;
+
+public class WorkflowFormQuery extends AbstractQuery {
+
+    private static final long serialVersionUID = -4762457303770028554L;
+
+    public static class Builder extends AbstractQuery.Builder<WorkflowFormQuery, Builder> {
+
+        @Override
+        protected WorkflowFormQuery newInstance() {
+            return new WorkflowFormQuery();
+        }
+    }
+}

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/common/rest-api/src/main/java/org/apache/syncope/common/rest/api/service/UserWorkflowService.java
----------------------------------------------------------------------
diff --git a/common/rest-api/src/main/java/org/apache/syncope/common/rest/api/service/UserWorkflowService.java b/common/rest-api/src/main/java/org/apache/syncope/common/rest/api/service/UserWorkflowService.java
index 7be582c..d89f250 100644
--- a/common/rest-api/src/main/java/org/apache/syncope/common/rest/api/service/UserWorkflowService.java
+++ b/common/rest-api/src/main/java/org/apache/syncope/common/rest/api/service/UserWorkflowService.java
@@ -22,6 +22,7 @@ import io.swagger.annotations.Api;
 import io.swagger.annotations.Authorization;
 import java.util.List;
 import javax.validation.constraints.NotNull;
+import javax.ws.rs.BeanParam;
 import javax.ws.rs.Consumes;
 import javax.ws.rs.GET;
 import javax.ws.rs.POST;
@@ -30,9 +31,11 @@ import javax.ws.rs.PathParam;
 import javax.ws.rs.Produces;
 import javax.ws.rs.core.MediaType;
 import org.apache.syncope.common.lib.SyncopeConstants;
+import org.apache.syncope.common.lib.to.PagedResult;
 import org.apache.syncope.common.lib.to.UserTO;
 import org.apache.syncope.common.lib.to.WorkflowFormTO;
 import org.apache.syncope.common.lib.to.WorkflowTaskTO;
+import org.apache.syncope.common.rest.api.beans.WorkflowFormQuery;
 
 /**
  * REST operations related to user workflow.
@@ -46,12 +49,13 @@ public interface UserWorkflowService extends JAXRSService {
     /**
      * Returns a list of all available workflow forms.
      *
+     * @param query query conditions
      * @return list of all available workflow forms
      */
     @GET
     @Path("forms")
     @Produces({ MediaType.APPLICATION_JSON, SyncopeConstants.APPLICATION_YAML, MediaType.APPLICATION_XML })
-    List<WorkflowFormTO> getForms();
+    PagedResult<WorkflowFormTO> getForms(@BeanParam WorkflowFormQuery query);
 
     /**
      * Returns a list of available forms for the given user key.

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/core/logic/src/main/java/org/apache/syncope/core/logic/UserWorkflowLogic.java
----------------------------------------------------------------------
diff --git a/core/logic/src/main/java/org/apache/syncope/core/logic/UserWorkflowLogic.java b/core/logic/src/main/java/org/apache/syncope/core/logic/UserWorkflowLogic.java
index 8725c82..dabf93b 100644
--- a/core/logic/src/main/java/org/apache/syncope/core/logic/UserWorkflowLogic.java
+++ b/core/logic/src/main/java/org/apache/syncope/core/logic/UserWorkflowLogic.java
@@ -29,6 +29,7 @@ import org.apache.syncope.common.lib.to.WorkflowFormTO;
 import org.apache.syncope.common.lib.to.WorkflowTaskTO;
 import org.apache.syncope.common.lib.types.StandardEntitlement;
 import org.apache.syncope.core.persistence.api.dao.UserDAO;
+import org.apache.syncope.core.persistence.api.dao.search.OrderByClause;
 import org.apache.syncope.core.persistence.api.entity.user.User;
 import org.apache.syncope.core.provisioning.api.propagation.PropagationManager;
 import org.apache.syncope.core.provisioning.api.propagation.PropagationTaskExecutor;
@@ -91,8 +92,12 @@ public class UserWorkflowLogic extends AbstractTransactionalLogic<WorkflowFormTO
 
     @PreAuthorize("hasRole('" + StandardEntitlement.WORKFLOW_FORM_LIST + "')")
     @Transactional(readOnly = true)
-    public List<WorkflowFormTO> getForms() {
-        return uwfAdapter.getForms();
+    public Pair<Integer, List<WorkflowFormTO>> getForms(
+            final int page,
+            final int size,
+            final List<OrderByClause> orderByClauses) {
+
+        return uwfAdapter.getForms(page, size, orderByClauses);
     }
 
     @PreAuthorize("hasRole('" + StandardEntitlement.WORKFLOW_TASK_LIST + "') "

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/core/rest-cxf/src/main/java/org/apache/syncope/core/rest/cxf/service/UserWorkflowServiceImpl.java
----------------------------------------------------------------------
diff --git a/core/rest-cxf/src/main/java/org/apache/syncope/core/rest/cxf/service/UserWorkflowServiceImpl.java b/core/rest-cxf/src/main/java/org/apache/syncope/core/rest/cxf/service/UserWorkflowServiceImpl.java
index 8022f36..7a25cb8 100644
--- a/core/rest-cxf/src/main/java/org/apache/syncope/core/rest/cxf/service/UserWorkflowServiceImpl.java
+++ b/core/rest-cxf/src/main/java/org/apache/syncope/core/rest/cxf/service/UserWorkflowServiceImpl.java
@@ -19,16 +19,19 @@
 package org.apache.syncope.core.rest.cxf.service;
 
 import java.util.List;
+import org.apache.commons.lang3.tuple.Pair;
+import org.apache.syncope.common.lib.to.PagedResult;
 import org.apache.syncope.common.lib.to.UserTO;
 import org.apache.syncope.common.lib.to.WorkflowFormTO;
 import org.apache.syncope.common.lib.to.WorkflowTaskTO;
+import org.apache.syncope.common.rest.api.beans.WorkflowFormQuery;
 import org.apache.syncope.common.rest.api.service.UserWorkflowService;
 import org.apache.syncope.core.logic.UserWorkflowLogic;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
 
 @Service
-public class UserWorkflowServiceImpl implements UserWorkflowService {
+public class UserWorkflowServiceImpl extends AbstractServiceImpl implements UserWorkflowService {
 
     @Autowired
     private UserWorkflowLogic logic;
@@ -49,8 +52,10 @@ public class UserWorkflowServiceImpl implements UserWorkflowService {
     }
 
     @Override
-    public List<WorkflowFormTO> getForms() {
-        return logic.getForms();
+    public PagedResult<WorkflowFormTO> getForms(final WorkflowFormQuery query) {
+        Pair<Integer, List<WorkflowFormTO>> result = logic.getForms(
+                query.getPage(), query.getSize(), getOrderByClauses(query.getOrderBy()));
+        return buildPagedResult(result.getRight(), query.getPage(), query.getSize(), result.getLeft());
     }
 
     @Override

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/core/workflow-activiti/src/main/java/org/apache/syncope/core/workflow/activiti/ActivitiUserWorkflowAdapter.java
----------------------------------------------------------------------
diff --git a/core/workflow-activiti/src/main/java/org/apache/syncope/core/workflow/activiti/ActivitiUserWorkflowAdapter.java b/core/workflow-activiti/src/main/java/org/apache/syncope/core/workflow/activiti/ActivitiUserWorkflowAdapter.java
index 123f8df..6d32464 100644
--- a/core/workflow-activiti/src/main/java/org/apache/syncope/core/workflow/activiti/ActivitiUserWorkflowAdapter.java
+++ b/core/workflow-activiti/src/main/java/org/apache/syncope/core/workflow/activiti/ActivitiUserWorkflowAdapter.java
@@ -48,12 +48,12 @@ import org.activiti.engine.history.HistoricActivityInstance;
 import org.activiti.engine.history.HistoricDetail;
 import org.activiti.engine.history.HistoricTaskInstance;
 import org.activiti.engine.impl.persistence.entity.HistoricFormPropertyEntity;
-import org.activiti.engine.query.Query;
 import org.activiti.engine.repository.Deployment;
 import org.activiti.engine.repository.Model;
 import org.activiti.engine.repository.ProcessDefinition;
 import org.activiti.engine.runtime.ProcessInstance;
 import org.activiti.engine.task.Task;
+import org.activiti.engine.task.TaskQuery;
 import org.apache.commons.collections4.CollectionUtils;
 import org.apache.commons.collections4.Transformer;
 import org.apache.commons.io.IOUtils;
@@ -75,6 +75,7 @@ import org.apache.syncope.core.spring.BeanUtils;
 import org.apache.syncope.core.persistence.api.attrvalue.validation.InvalidEntityException;
 import org.apache.syncope.core.persistence.api.attrvalue.validation.ParsingValidationException;
 import org.apache.syncope.core.persistence.api.dao.NotFoundException;
+import org.apache.syncope.core.persistence.api.dao.search.OrderByClause;
 import org.apache.syncope.core.persistence.api.entity.user.User;
 import org.apache.syncope.core.provisioning.api.WorkflowResult;
 import org.apache.syncope.core.workflow.activiti.spring.DomainProcessEngine;
@@ -605,56 +606,88 @@ public class ActivitiUserWorkflowAdapter extends AbstractUserWorkflowAdapter {
 
     @Transactional(readOnly = true)
     @Override
-    public List<WorkflowFormTO> getForms() {
-        List<WorkflowFormTO> forms = new ArrayList<>();
+    public Pair<Integer, List<WorkflowFormTO>> getForms(
+            final int page, final int size, final List<OrderByClause> orderByClauses) {
+
+        Pair<Integer, List<WorkflowFormTO>> forms = null;
 
         String authUser = AuthContextUtils.getUsername();
         if (adminUser.equals(authUser)) {
-            forms.addAll(getForms(engine.getTaskService().createTaskQuery().
-                    taskVariableValueEquals(TASK_IS_FORM, Boolean.TRUE)));
+            forms = getForms(engine.getTaskService().createTaskQuery().
+                    taskVariableValueEquals(TASK_IS_FORM, Boolean.TRUE), page, size, orderByClauses);
         } else {
             User user = userDAO.findByUsername(authUser);
             if (user == null) {
                 throw new NotFoundException("Syncope User " + authUser);
             }
 
-            forms.addAll(getForms(engine.getTaskService().createTaskQuery().
+            forms = getForms(engine.getTaskService().createTaskQuery().
                     taskVariableValueEquals(TASK_IS_FORM, Boolean.TRUE).
-                    taskCandidateOrAssigned(user.getKey())));
+                    taskCandidateOrAssigned(user.getKey()), page, size, orderByClauses);
 
             List<String> candidateGroups = new ArrayList<>();
             for (String groupName : userDAO.findAllGroupNames(user)) {
                 candidateGroups.add(groupName);
             }
             if (!candidateGroups.isEmpty()) {
-                forms.addAll(getForms(engine.getTaskService().createTaskQuery().
+                forms = getForms(engine.getTaskService().createTaskQuery().
                         taskVariableValueEquals(TASK_IS_FORM, Boolean.TRUE).
-                        taskCandidateGroupIn(candidateGroups)));
+                        taskCandidateGroupIn(candidateGroups), page, size, orderByClauses);
             }
         }
 
-        return forms;
+        return forms == null
+                ? Pair.of(0, Collections.<WorkflowFormTO>emptyList())
+                : forms;
     }
 
-    protected <T extends Query<?, ?>, U extends Object> List<WorkflowFormTO> getForms(final Query<T, U> query) {
-        List<WorkflowFormTO> forms = new ArrayList<>();
+    protected Pair<Integer, List<WorkflowFormTO>> getForms(
+            final TaskQuery query, final int page, final int size, final List<OrderByClause> orderByClauses) {
 
-        for (U obj : query.list()) {
-            try {
-                if (obj instanceof HistoricTaskInstance) {
-                    forms.add(getFormTO((HistoricTaskInstance) obj));
-                } else if (obj instanceof Task) {
-                    forms.add(getFormTO((Task) obj));
+        TaskQuery sortedQuery = query;
+        for (OrderByClause clause : orderByClauses) {
+            boolean ack = true;
+            switch (clause.getField().trim()) {
+                case "taskId":
+                    sortedQuery = sortedQuery.orderByTaskId();
+                    break;
+
+                case "createTime":
+                    sortedQuery = sortedQuery.orderByTaskCreateTime();
+                    break;
+
+                case "dueDate":
+                    sortedQuery = sortedQuery.orderByTaskDueDate();
+                    break;
+
+                case "owner":
+                    sortedQuery = sortedQuery.orderByTaskOwner();
+                    break;
+
+                default:
+                    LOG.warn("Form sort request by {}: unsupported, ignoring", clause.getField().trim());
+                    ack = false;
+            }
+            if (ack) {
+                if (clause.getDirection() == OrderByClause.Direction.ASC) {
+                    sortedQuery = sortedQuery.asc();
                 } else {
-                    throw new ActivitiException(
-                            "Failure retrieving form", new IllegalArgumentException("Invalid task type"));
+                    sortedQuery = sortedQuery.desc();
                 }
-            } catch (ActivitiException e) {
-                LOG.debug("No form found for task {}", obj, e);
             }
         }
 
-        return forms;
+        List<WorkflowFormTO> result = new ArrayList<>();
+
+        for (Task task : sortedQuery.listPage(size * (page <= 0 ? 0 : page - 1), size)) {
+            if (task instanceof HistoricTaskInstance) {
+                result.add(getFormTO((HistoricTaskInstance) task));
+            } else {
+                result.add(getFormTO(task));
+            }
+        }
+
+        return Pair.of((int) query.count(), result);
     }
 
     @Override

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/core/workflow-api/src/main/java/org/apache/syncope/core/workflow/api/WorkflowAdapter.java
----------------------------------------------------------------------
diff --git a/core/workflow-api/src/main/java/org/apache/syncope/core/workflow/api/WorkflowAdapter.java b/core/workflow-api/src/main/java/org/apache/syncope/core/workflow/api/WorkflowAdapter.java
index 2f2f273..515d05f 100644
--- a/core/workflow-api/src/main/java/org/apache/syncope/core/workflow/api/WorkflowAdapter.java
+++ b/core/workflow-api/src/main/java/org/apache/syncope/core/workflow/api/WorkflowAdapter.java
@@ -19,9 +19,11 @@
 package org.apache.syncope.core.workflow.api;
 
 import java.util.List;
+import org.apache.commons.lang3.tuple.Pair;
 import org.apache.syncope.common.lib.patch.AnyPatch;
 import org.apache.syncope.common.lib.to.WorkflowFormTO;
 import org.apache.syncope.common.lib.to.WorkflowTaskTO;
+import org.apache.syncope.core.persistence.api.dao.search.OrderByClause;
 import org.apache.syncope.core.provisioning.api.WorkflowResult;
 
 public interface WorkflowAdapter {
@@ -37,11 +39,14 @@ public interface WorkflowAdapter {
     String getPrefix();
 
     /**
-     * Get all defined forms for current workflow process instances.
+     * Get the forms for current workflow process instances matching the provided parameters.
      *
-     * @return list of defined forms
+     * @param page result page
+     * @param size items per page
+     * @param orderByClauses sort conditions
+     * @return total number of forms, list of forms matching the provided parameters
      */
-    List<WorkflowFormTO> getForms();
+    Pair<Integer, List<WorkflowFormTO>> getForms(int page, int size, List<OrderByClause> orderByClauses);
 
     /**
      * Get form for given workflowId (if present).
@@ -69,7 +74,7 @@ public interface WorkflowAdapter {
 
     /**
      * Get tasks available for execution, for given workflow id.
-     * 
+     *
      * @param workflowId workflow id
      * @return available tasks
      */

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/core/workflow-flowable/src/main/java/org/apache/syncope/core/workflow/flowable/FlowableUserWorkflowAdapter.java
----------------------------------------------------------------------
diff --git a/core/workflow-flowable/src/main/java/org/apache/syncope/core/workflow/flowable/FlowableUserWorkflowAdapter.java b/core/workflow-flowable/src/main/java/org/apache/syncope/core/workflow/flowable/FlowableUserWorkflowAdapter.java
index 8755572..1e651db 100644
--- a/core/workflow-flowable/src/main/java/org/apache/syncope/core/workflow/flowable/FlowableUserWorkflowAdapter.java
+++ b/core/workflow-flowable/src/main/java/org/apache/syncope/core/workflow/flowable/FlowableUserWorkflowAdapter.java
@@ -47,12 +47,12 @@ import org.activiti.engine.history.HistoricActivityInstance;
 import org.activiti.engine.history.HistoricDetail;
 import org.activiti.engine.history.HistoricTaskInstance;
 import org.activiti.engine.impl.persistence.entity.HistoricFormPropertyEntity;
-import org.activiti.engine.query.Query;
 import org.activiti.engine.repository.Deployment;
 import org.activiti.engine.repository.Model;
 import org.activiti.engine.repository.ProcessDefinition;
 import org.activiti.engine.runtime.ProcessInstance;
 import org.activiti.engine.task.Task;
+import org.activiti.engine.task.TaskQuery;
 import org.apache.commons.collections4.CollectionUtils;
 import org.apache.commons.collections4.Transformer;
 import org.apache.commons.io.IOUtils;
@@ -74,6 +74,7 @@ import org.apache.syncope.core.spring.BeanUtils;
 import org.apache.syncope.core.persistence.api.attrvalue.validation.InvalidEntityException;
 import org.apache.syncope.core.persistence.api.attrvalue.validation.ParsingValidationException;
 import org.apache.syncope.core.persistence.api.dao.NotFoundException;
+import org.apache.syncope.core.persistence.api.dao.search.OrderByClause;
 import org.apache.syncope.core.persistence.api.entity.user.User;
 import org.apache.syncope.core.provisioning.api.WorkflowResult;
 import org.apache.syncope.core.workflow.flowable.spring.DomainProcessEngine;
@@ -604,56 +605,88 @@ public class FlowableUserWorkflowAdapter extends AbstractUserWorkflowAdapter {
 
     @Transactional(readOnly = true)
     @Override
-    public List<WorkflowFormTO> getForms() {
-        List<WorkflowFormTO> forms = new ArrayList<>();
+    public Pair<Integer, List<WorkflowFormTO>> getForms(
+            final int page, final int size, final List<OrderByClause> orderByClauses) {
+
+        Pair<Integer, List<WorkflowFormTO>> forms = null;
 
         String authUser = AuthContextUtils.getUsername();
         if (adminUser.equals(authUser)) {
-            forms.addAll(getForms(engine.getTaskService().createTaskQuery().
-                    taskVariableValueEquals(TASK_IS_FORM, Boolean.TRUE)));
+            forms = getForms(engine.getTaskService().createTaskQuery().
+                    taskVariableValueEquals(TASK_IS_FORM, Boolean.TRUE), page, size, orderByClauses);
         } else {
             User user = userDAO.findByUsername(authUser);
             if (user == null) {
                 throw new NotFoundException("Syncope User " + authUser);
             }
 
-            forms.addAll(getForms(engine.getTaskService().createTaskQuery().
+            forms = getForms(engine.getTaskService().createTaskQuery().
                     taskVariableValueEquals(TASK_IS_FORM, Boolean.TRUE).
-                    taskCandidateOrAssigned(user.getKey())));
+                    taskCandidateOrAssigned(user.getKey()), page, size, orderByClauses);
 
             List<String> candidateGroups = new ArrayList<>();
             for (String groupName : userDAO.findAllGroupNames(user)) {
                 candidateGroups.add(groupName);
             }
             if (!candidateGroups.isEmpty()) {
-                forms.addAll(getForms(engine.getTaskService().createTaskQuery().
+                forms = getForms(engine.getTaskService().createTaskQuery().
                         taskVariableValueEquals(TASK_IS_FORM, Boolean.TRUE).
-                        taskCandidateGroupIn(candidateGroups)));
+                        taskCandidateGroupIn(candidateGroups), page, size, orderByClauses);
             }
         }
 
-        return forms;
+        return forms == null
+                ? Pair.of(0, Collections.<WorkflowFormTO>emptyList())
+                : forms;
     }
 
-    protected <T extends Query<?, ?>, U extends Object> List<WorkflowFormTO> getForms(final Query<T, U> query) {
-        List<WorkflowFormTO> forms = new ArrayList<>();
+    protected Pair<Integer, List<WorkflowFormTO>> getForms(
+            final TaskQuery query, final int page, final int size, final List<OrderByClause> orderByClauses) {
 
-        for (U obj : query.list()) {
-            try {
-                if (obj instanceof HistoricTaskInstance) {
-                    forms.add(getFormTO((HistoricTaskInstance) obj));
-                } else if (obj instanceof Task) {
-                    forms.add(getFormTO((Task) obj));
+        TaskQuery sortedQuery = query;
+        for (OrderByClause clause : orderByClauses) {
+            boolean ack = true;
+            switch (clause.getField().trim()) {
+                case "taskId":
+                    sortedQuery = sortedQuery.orderByTaskId();
+                    break;
+
+                case "createTime":
+                    sortedQuery = sortedQuery.orderByTaskCreateTime();
+                    break;
+
+                case "dueDate":
+                    sortedQuery = sortedQuery.orderByTaskDueDate();
+                    break;
+
+                case "owner":
+                    sortedQuery = sortedQuery.orderByTaskOwner();
+                    break;
+
+                default:
+                    LOG.warn("Form sort request by {}: unsupported, ignoring", clause.getField().trim());
+                    ack = false;
+            }
+            if (ack) {
+                if (clause.getDirection() == OrderByClause.Direction.ASC) {
+                    sortedQuery = sortedQuery.asc();
                 } else {
-                    throw new ActivitiException(
-                            "Failure retrieving form", new IllegalArgumentException("Invalid task type"));
+                    sortedQuery = sortedQuery.desc();
                 }
-            } catch (ActivitiException e) {
-                LOG.debug("No form found for task {}", obj, e);
             }
         }
 
-        return forms;
+        List<WorkflowFormTO> result = new ArrayList<>();
+
+        for (Task task : sortedQuery.listPage(size * (page <= 0 ? 0 : page - 1), size)) {
+            if (task instanceof HistoricTaskInstance) {
+                result.add(getFormTO((HistoricTaskInstance) task));
+            } else {
+                result.add(getFormTO(task));
+            }
+        }
+
+        return Pair.of((int) query.count(), result);
     }
 
     @Override

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/core/workflow-java/src/main/java/org/apache/syncope/core/workflow/java/DefaultAnyObjectWorkflowAdapter.java
----------------------------------------------------------------------
diff --git a/core/workflow-java/src/main/java/org/apache/syncope/core/workflow/java/DefaultAnyObjectWorkflowAdapter.java b/core/workflow-java/src/main/java/org/apache/syncope/core/workflow/java/DefaultAnyObjectWorkflowAdapter.java
index eac899a..200866a 100644
--- a/core/workflow-java/src/main/java/org/apache/syncope/core/workflow/java/DefaultAnyObjectWorkflowAdapter.java
+++ b/core/workflow-java/src/main/java/org/apache/syncope/core/workflow/java/DefaultAnyObjectWorkflowAdapter.java
@@ -21,6 +21,7 @@ package org.apache.syncope.core.workflow.java;
 import java.io.OutputStream;
 import java.util.Collections;
 import java.util.List;
+import org.apache.commons.lang3.tuple.Pair;
 import org.apache.syncope.common.lib.patch.AnyObjectPatch;
 import org.apache.syncope.common.lib.to.AnyObjectTO;
 import org.apache.syncope.common.lib.to.WorkflowDefinitionTO;
@@ -28,6 +29,7 @@ import org.apache.syncope.common.lib.to.WorkflowFormTO;
 import org.apache.syncope.common.lib.to.WorkflowTaskTO;
 import org.apache.syncope.core.provisioning.api.PropagationByResource;
 import org.apache.syncope.common.lib.types.ResourceOperation;
+import org.apache.syncope.core.persistence.api.dao.search.OrderByClause;
 import org.apache.syncope.core.persistence.api.entity.anyobject.AnyObject;
 import org.apache.syncope.core.provisioning.api.WorkflowResult;
 import org.apache.syncope.core.workflow.api.WorkflowDefinitionFormat;
@@ -72,8 +74,10 @@ public class DefaultAnyObjectWorkflowAdapter extends AbstractAnyObjectWorkflowAd
     }
 
     @Override
-    public List<WorkflowFormTO> getForms() {
-        return Collections.emptyList();
+    public Pair<Integer, List<WorkflowFormTO>> getForms(
+            final int page, final int size, List<OrderByClause> orderByClauses) {
+
+        return Pair.of(0, Collections.<WorkflowFormTO>emptyList());
     }
 
     @Override

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/core/workflow-java/src/main/java/org/apache/syncope/core/workflow/java/DefaultGroupWorkflowAdapter.java
----------------------------------------------------------------------
diff --git a/core/workflow-java/src/main/java/org/apache/syncope/core/workflow/java/DefaultGroupWorkflowAdapter.java b/core/workflow-java/src/main/java/org/apache/syncope/core/workflow/java/DefaultGroupWorkflowAdapter.java
index d430200..ad5aa4b 100644
--- a/core/workflow-java/src/main/java/org/apache/syncope/core/workflow/java/DefaultGroupWorkflowAdapter.java
+++ b/core/workflow-java/src/main/java/org/apache/syncope/core/workflow/java/DefaultGroupWorkflowAdapter.java
@@ -21,6 +21,7 @@ package org.apache.syncope.core.workflow.java;
 import java.io.OutputStream;
 import java.util.Collections;
 import java.util.List;
+import org.apache.commons.lang3.tuple.Pair;
 import org.apache.syncope.common.lib.patch.GroupPatch;
 import org.apache.syncope.common.lib.to.GroupTO;
 import org.apache.syncope.common.lib.to.WorkflowDefinitionTO;
@@ -28,6 +29,7 @@ import org.apache.syncope.common.lib.to.WorkflowFormTO;
 import org.apache.syncope.common.lib.to.WorkflowTaskTO;
 import org.apache.syncope.core.provisioning.api.PropagationByResource;
 import org.apache.syncope.common.lib.types.ResourceOperation;
+import org.apache.syncope.core.persistence.api.dao.search.OrderByClause;
 import org.apache.syncope.core.persistence.api.entity.group.Group;
 import org.apache.syncope.core.provisioning.api.WorkflowResult;
 import org.apache.syncope.core.workflow.api.WorkflowDefinitionFormat;
@@ -72,8 +74,10 @@ public class DefaultGroupWorkflowAdapter extends AbstractGroupWorkflowAdapter {
     }
 
     @Override
-    public List<WorkflowFormTO> getForms() {
-        return Collections.emptyList();
+    public Pair<Integer, List<WorkflowFormTO>> getForms(
+            final int page, final int size, List<OrderByClause> orderByClauses) {
+
+        return Pair.of(0, Collections.<WorkflowFormTO>emptyList());
     }
 
     @Override

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/core/workflow-java/src/main/java/org/apache/syncope/core/workflow/java/DefaultUserWorkflowAdapter.java
----------------------------------------------------------------------
diff --git a/core/workflow-java/src/main/java/org/apache/syncope/core/workflow/java/DefaultUserWorkflowAdapter.java b/core/workflow-java/src/main/java/org/apache/syncope/core/workflow/java/DefaultUserWorkflowAdapter.java
index c055d8f..727ca30 100644
--- a/core/workflow-java/src/main/java/org/apache/syncope/core/workflow/java/DefaultUserWorkflowAdapter.java
+++ b/core/workflow-java/src/main/java/org/apache/syncope/core/workflow/java/DefaultUserWorkflowAdapter.java
@@ -31,6 +31,7 @@ import org.apache.syncope.common.lib.to.WorkflowTaskTO;
 import org.apache.syncope.core.provisioning.api.PropagationByResource;
 import org.apache.syncope.common.lib.types.ResourceOperation;
 import org.apache.syncope.core.persistence.api.dao.ConfDAO;
+import org.apache.syncope.core.persistence.api.dao.search.OrderByClause;
 import org.apache.syncope.core.persistence.api.entity.user.User;
 import org.apache.syncope.core.provisioning.api.WorkflowResult;
 import org.apache.syncope.core.workflow.api.WorkflowDefinitionFormat;
@@ -161,8 +162,10 @@ public class DefaultUserWorkflowAdapter extends AbstractUserWorkflowAdapter {
     }
 
     @Override
-    public List<WorkflowFormTO> getForms() {
-        return Collections.emptyList();
+    public Pair<Integer, List<WorkflowFormTO>> getForms(
+            final int page, final int size, List<OrderByClause> orderByClauses) {
+
+        return Pair.of(0, Collections.<WorkflowFormTO>emptyList());
     }
 
     @Override

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/fit/core-reference/src/test/java/org/apache/syncope/fit/core/SchedTaskITCase.java
----------------------------------------------------------------------
diff --git a/fit/core-reference/src/test/java/org/apache/syncope/fit/core/SchedTaskITCase.java b/fit/core-reference/src/test/java/org/apache/syncope/fit/core/SchedTaskITCase.java
index 3c1aa64..ec1fe71 100644
--- a/fit/core-reference/src/test/java/org/apache/syncope/fit/core/SchedTaskITCase.java
+++ b/fit/core-reference/src/test/java/org/apache/syncope/fit/core/SchedTaskITCase.java
@@ -46,6 +46,7 @@ import org.apache.syncope.common.lib.types.TaskType;
 import org.apache.syncope.common.rest.api.beans.ExecuteQuery;
 import org.apache.syncope.common.rest.api.beans.ExecQuery;
 import org.apache.syncope.common.rest.api.beans.TaskQuery;
+import org.apache.syncope.common.rest.api.beans.WorkflowFormQuery;
 import org.apache.syncope.common.rest.api.service.TaskService;
 import org.apache.syncope.fit.ActivitiDetector;
 import org.apache.syncope.fit.core.reference.TestSampleJobDelegate;
@@ -138,7 +139,8 @@ public class SchedTaskITCase extends AbstractTaskITCase {
 
         execTask(taskService, TaskType.SCHEDULED, "e95555d2-1b09-42c8-b25b-f4c4ec598989", "JOB_FIRED", 50, false);
 
-        List<WorkflowFormTO> forms = userWorkflowService.getForms();
+        List<WorkflowFormTO> forms = userWorkflowService.getForms(
+                new WorkflowFormQuery.Builder().page(1).size(1000).build()).getResult();
         assertFalse(forms.isEmpty());
         for (WorkflowFormTO form : forms) {
             userWorkflowService.claimForm(form.getTaskId());
@@ -147,7 +149,8 @@ public class SchedTaskITCase extends AbstractTaskITCase {
             userWorkflowService.submitForm(form);
         }
 
-        forms = userWorkflowService.getForms();
+        forms = userWorkflowService.getForms(
+                new WorkflowFormQuery.Builder().page(1).size(1000).build()).getResult();
         assertTrue(forms.isEmpty());
     }
 

http://git-wip-us.apache.org/repos/asf/syncope/blob/6db41512/fit/core-reference/src/test/java/org/apache/syncope/fit/core/UserWorkflowITCase.java
----------------------------------------------------------------------
diff --git a/fit/core-reference/src/test/java/org/apache/syncope/fit/core/UserWorkflowITCase.java b/fit/core-reference/src/test/java/org/apache/syncope/fit/core/UserWorkflowITCase.java
index dadaf29..0338105 100644
--- a/fit/core-reference/src/test/java/org/apache/syncope/fit/core/UserWorkflowITCase.java
+++ b/fit/core-reference/src/test/java/org/apache/syncope/fit/core/UserWorkflowITCase.java
@@ -42,12 +42,14 @@ import org.apache.syncope.common.lib.patch.StringPatchItem;
 import org.apache.syncope.common.lib.patch.StringReplacePatchItem;
 import org.apache.syncope.common.lib.patch.UserPatch;
 import org.apache.syncope.common.lib.to.MembershipTO;
+import org.apache.syncope.common.lib.to.PagedResult;
 import org.apache.syncope.common.lib.to.ProvisioningResult;
 import org.apache.syncope.common.lib.to.UserTO;
 import org.apache.syncope.common.lib.to.WorkflowFormTO;
 import org.apache.syncope.common.lib.to.WorkflowTaskTO;
 import org.apache.syncope.common.lib.types.ClientExceptionType;
 import org.apache.syncope.common.lib.types.PatchOperation;
+import org.apache.syncope.common.rest.api.beans.WorkflowFormQuery;
 import org.apache.syncope.common.rest.api.service.UserSelfService;
 import org.apache.syncope.common.rest.api.service.UserWorkflowService;
 import org.apache.syncope.fit.AbstractITCase;
@@ -146,9 +148,9 @@ public class UserWorkflowITCase extends AbstractITCase {
         Assume.assumeTrue(ActivitiDetector.isActivitiEnabledForUsers(syncopeService));
 
         // read forms *before* any operation
-        List<WorkflowFormTO> forms = userWorkflowService.getForms();
-        assertNotNull(forms);
-        int preForms = forms.size();
+        PagedResult<WorkflowFormTO> forms =
+                userWorkflowService.getForms(new WorkflowFormQuery.Builder().page(1).size(1000).build());
+        int preForms = forms.getTotalCount();
 
         UserTO userTO = UserITCase.getUniqueSampleTO("createWithApproval@syncope.apache.org");
         userTO.getResources().add(RESOURCE_NAME_TESTDB);
@@ -180,9 +182,8 @@ public class UserWorkflowITCase extends AbstractITCase {
         assertNotNull(exception);
 
         // 2. request if there is any pending form for user just created
-        forms = userWorkflowService.getForms();
-        assertNotNull(forms);
-        assertEquals(preForms + 1, forms.size());
+        forms = userWorkflowService.getForms(new WorkflowFormQuery.Builder().page(1).size(1000).build());
+        assertEquals(preForms + 1, forms.getTotalCount());
 
         // 3. as admin, request for changes: still pending approval
         String updatedUsername = "changed-" + UUID.randomUUID().toString();
@@ -232,9 +233,9 @@ public class UserWorkflowITCase extends AbstractITCase {
         Assume.assumeTrue(ActivitiDetector.isActivitiEnabledForUsers(syncopeService));
 
         // read forms *before* any operation
-        List<WorkflowFormTO> forms = userWorkflowService.getForms();
-        assertNotNull(forms);
-        int preForms = forms.size();
+        PagedResult<WorkflowFormTO> forms = userWorkflowService.getForms(
+                new WorkflowFormQuery.Builder().page(1).size(1000).build());
+        int preForms = forms.getTotalCount();
 
         UserTO created = createUser(UserITCase.getUniqueSampleTO("updateApproval@syncope.apache.org")).getEntity();
         assertNotNull(created);
@@ -250,9 +251,8 @@ public class UserWorkflowITCase extends AbstractITCase {
         assertEquals(Response.Status.OK.getStatusCode(), response.getStatus());
         assertEquals("updateApproval", userService.read(created.getKey()).getStatus());
 
-        forms = userWorkflowService.getForms();
-        assertNotNull(forms);
-        assertEquals(preForms + 1, forms.size());
+        forms = userWorkflowService.getForms(new WorkflowFormQuery.Builder().page(1).size(1000).build());
+        assertEquals(preForms + 1, forms.getTotalCount());
 
         WorkflowFormTO form = userWorkflowService.getFormForUser(created.getKey());
         assertNotNull(form);
@@ -322,9 +322,9 @@ public class UserWorkflowITCase extends AbstractITCase {
         Assume.assumeTrue(ActivitiDetector.isActivitiEnabledForUsers(syncopeService));
 
         // read forms *before* any operation
-        List<WorkflowFormTO> forms = userWorkflowService.getForms();
-        assertNotNull(forms);
-        int preForms = forms.size();
+        PagedResult<WorkflowFormTO> forms = userWorkflowService.getForms(
+                new WorkflowFormQuery.Builder().page(1).size(1000).build());
+        int preForms = forms.getTotalCount();
 
         UserTO userTO = UserITCase.getUniqueSampleTO("issueSYNCOPE15@syncope.apache.org");
         userTO.getResources().clear();
@@ -347,8 +347,8 @@ public class UserWorkflowITCase extends AbstractITCase {
         assertEquals(userTO.getCreationDate(), userTO.getLastChangeDate());
 
         // 2. request if there is any pending form for user just created
-        forms = userWorkflowService.getForms();
-        assertEquals(preForms + 1, forms.size());
+        forms = userWorkflowService.getForms(new WorkflowFormQuery.Builder().page(1).size(1000).build());
+        assertEquals(preForms + 1, forms.getTotalCount());
 
         WorkflowFormTO form = userWorkflowService.getFormForUser(userTO.getKey());
         assertNotNull(form);
@@ -371,12 +371,14 @@ public class UserWorkflowITCase extends AbstractITCase {
         // 6. submit approve
         userTO = userWorkflowService.submitForm(form);
         assertNotNull(userTO);
-        assertEquals(preForms, userWorkflowService.getForms().size());
+        assertEquals(
+                preForms,
+                userWorkflowService.getForms(
+                        new WorkflowFormQuery.Builder().page(1).size(1000).build()).getTotalCount());
         assertNull(userWorkflowService.getFormForUser(userTO.getKey()));
 
         // 7.check that no more forms are still to be processed
-        forms = userWorkflowService.getForms();
-        assertEquals(preForms, forms.size());
+        forms = userWorkflowService.getForms(new WorkflowFormQuery.Builder().page(1).size(1000).build());
+        assertEquals(preForms, forms.getTotalCount());
     }
-
 }