diff --git a/gms/src/main/java/it/inaf/ia2/gms/controller/GroupsController.java b/gms/src/main/java/it/inaf/ia2/gms/controller/GroupsController.java
index 0c894e2f6b2ef2496a81c0c13ce64131b5657a23..82803dfe49ea23a29b02ac9d2be8491f5bb09d71 100644
--- a/gms/src/main/java/it/inaf/ia2/gms/controller/GroupsController.java
+++ b/gms/src/main/java/it/inaf/ia2/gms/controller/GroupsController.java
@@ -2,16 +2,15 @@ package it.inaf.ia2.gms.controller;
 
 import it.inaf.ia2.gms.authn.SessionData;
 import it.inaf.ia2.gms.exception.UnauthorizedException;
-import it.inaf.ia2.gms.model.CreateGroupRequest;
+import it.inaf.ia2.gms.model.request.AddGroupRequest;
 import it.inaf.ia2.gms.model.GroupNode;
-import it.inaf.ia2.gms.model.GroupsModelRequest;
-import it.inaf.ia2.gms.model.GroupsModelResponse;
-import it.inaf.ia2.gms.model.PaginatedData;
-import it.inaf.ia2.gms.model.PaginatedModelRequest;
+import it.inaf.ia2.gms.model.request.TabRequest;
+import it.inaf.ia2.gms.model.response.PaginatedData;
+import it.inaf.ia2.gms.model.request.PaginatedModelRequest;
 import it.inaf.ia2.gms.model.Permission;
-import it.inaf.ia2.gms.model.RenameGroupRequest;
+import it.inaf.ia2.gms.model.request.RenameGroupRequest;
+import it.inaf.ia2.gms.model.response.GroupsTabResponse;
 import it.inaf.ia2.gms.persistence.model.GroupEntity;
-import it.inaf.ia2.gms.service.GroupsModelBuilder;
 import it.inaf.ia2.gms.service.GroupsService;
 import it.inaf.ia2.gms.service.GroupsTreeBuilder;
 import it.inaf.ia2.gms.service.PermissionsService;
@@ -41,18 +40,18 @@ public class GroupsController {
     private GroupsService groupsService;
 
     @Autowired
-    private GroupsModelBuilder groupsModelService;
+    private GroupsTreeBuilder groupsTreeBuilder;
 
     @Autowired
-    private GroupsTreeBuilder groupsTreeBuilder;
+    private GroupsTabResponseBuilder groupsTabResponseBuilder;
 
     @GetMapping(value = "/groups", produces = MediaType.APPLICATION_JSON_UTF8_VALUE)
-    public GroupsModelResponse getGroupsModelResponse(@Valid GroupsModelRequest groupsModelRequest) {
-        return groupsModelService.getGroupsModel(groupsModelRequest, session.getUserId());
+    public ResponseEntity<GroupsTabResponse> getGroupsTab(@Valid TabRequest request) {
+        return ResponseEntity.ok(groupsTabResponseBuilder.getGroupsTab(request));
     }
 
     @PostMapping(value = "/group", consumes = MediaType.APPLICATION_JSON_UTF8_VALUE, produces = MediaType.APPLICATION_JSON_UTF8_VALUE)
-    public ResponseEntity<PaginatedData<GroupNode>> createGroup(@Valid @RequestBody CreateGroupRequest request) {
+    public ResponseEntity<PaginatedData<GroupNode>> createGroup(@Valid @RequestBody AddGroupRequest request) {
 
         GroupEntity parent = groupsService.getGroupById(request.getParentGroupId());
 
@@ -60,7 +59,7 @@ public class GroupsController {
             throw new UnauthorizedException("Missing admin permission");
         }
 
-        GroupEntity newGroup = groupsService.addGroup(parent, request.getNewGroupName());
+        groupsService.addGroup(parent, request.getNewGroupName());
 
         PaginatedData<GroupNode> groupsPanel = getGroupsPanel(request.getParentGroupId(), request);
 
diff --git a/gms/src/main/java/it/inaf/ia2/gms/controller/GroupsTabResponseBuilder.java b/gms/src/main/java/it/inaf/ia2/gms/controller/GroupsTabResponseBuilder.java
new file mode 100644
index 0000000000000000000000000000000000000000..420fe2a70fbaaa8fc2c97393dbc0f44b6e41b11d
--- /dev/null
+++ b/gms/src/main/java/it/inaf/ia2/gms/controller/GroupsTabResponseBuilder.java
@@ -0,0 +1,44 @@
+package it.inaf.ia2.gms.controller;
+
+import it.inaf.ia2.gms.authn.SessionData;
+import it.inaf.ia2.gms.model.Permission;
+import it.inaf.ia2.gms.model.request.TabRequest;
+import it.inaf.ia2.gms.model.response.GroupsTabResponse;
+import it.inaf.ia2.gms.persistence.model.GroupEntity;
+import it.inaf.ia2.gms.service.GroupsService;
+import it.inaf.ia2.gms.service.GroupsTreeBuilder;
+import it.inaf.ia2.gms.service.PermissionsService;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Component;
+
+@Component
+public class GroupsTabResponseBuilder {
+
+    @Autowired
+    private SessionData session;
+
+    @Autowired
+    private PermissionsService permissionsService;
+
+    @Autowired
+    private GroupsService groupsService;
+
+    @Autowired
+    private GroupsTreeBuilder groupsTreeBuilder;
+
+    public GroupsTabResponse getGroupsTab(TabRequest request) {
+
+        GroupEntity group = groupsService.getGroupById(request.getGroupId());
+
+        GroupsTabResponse response = new GroupsTabResponse();
+
+        response.setBreadcrumbs(groupsService.getBreadcrumbs(group.getPath()));
+
+        Permission currentNodePermissions = permissionsService.getUserPermissionForGroup(group, session.getUserId());
+        response.setPermission(currentNodePermissions);
+
+        response.setGroupsPanel(groupsTreeBuilder.listSubGroups(group.getId(), session.getUserId(), request));
+
+        return response;
+    }
+}
diff --git a/gms/src/main/java/it/inaf/ia2/gms/controller/HomePageController.java b/gms/src/main/java/it/inaf/ia2/gms/controller/HomePageController.java
new file mode 100644
index 0000000000000000000000000000000000000000..6ad84e213d1cb5a7f2f7290285c29869f6be8f75
--- /dev/null
+++ b/gms/src/main/java/it/inaf/ia2/gms/controller/HomePageController.java
@@ -0,0 +1,39 @@
+package it.inaf.ia2.gms.controller;
+
+import it.inaf.ia2.gms.authn.SessionData;
+import it.inaf.ia2.gms.model.request.TabRequest;
+import it.inaf.ia2.gms.model.response.GroupsTabResponse;
+import it.inaf.ia2.gms.model.response.HomePageResponse;
+import javax.validation.Valid;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.http.MediaType;
+import org.springframework.http.ResponseEntity;
+import org.springframework.stereotype.Controller;
+import org.springframework.web.bind.annotation.GetMapping;
+import org.springframework.web.bind.annotation.ResponseBody;
+
+@Controller
+public class HomePageController {
+
+    @Autowired
+    private SessionData session;
+
+    @Autowired
+    private GroupsTabResponseBuilder groupsTabResponseBuilder;
+
+    @ResponseBody
+    @GetMapping(value = "/home", produces = MediaType.APPLICATION_JSON_UTF8_VALUE)
+    public ResponseEntity<HomePageResponse> getMainPage(@Valid TabRequest request) {
+
+        HomePageResponse response = new HomePageResponse();
+
+        response.setUser(session.getUserId());
+
+        GroupsTabResponse groupsTabResponse = groupsTabResponseBuilder.getGroupsTab(request);
+        response.setBreadcrumbs(groupsTabResponse.getBreadcrumbs());
+        response.setGroupsPanel(groupsTabResponse.getGroupsPanel());
+        response.setPermission(groupsTabResponse.getPermission());
+
+        return ResponseEntity.ok(response);
+    }
+}
diff --git a/gms/src/main/java/it/inaf/ia2/gms/controller/MembersController.java b/gms/src/main/java/it/inaf/ia2/gms/controller/MembersController.java
index d6069b18956a2c410f178fdde62c0acc02145779..df39a439356f87bb055afc69abf4af5dd92c90c8 100644
--- a/gms/src/main/java/it/inaf/ia2/gms/controller/MembersController.java
+++ b/gms/src/main/java/it/inaf/ia2/gms/controller/MembersController.java
@@ -2,12 +2,13 @@ package it.inaf.ia2.gms.controller;
 
 import it.inaf.ia2.gms.authn.SessionData;
 import it.inaf.ia2.gms.exception.UnauthorizedException;
-import it.inaf.ia2.gms.model.AddMemberRequest;
-import it.inaf.ia2.gms.model.MemberRequest;
-import it.inaf.ia2.gms.model.PaginatedData;
+import it.inaf.ia2.gms.model.request.AddMemberRequest;
+import it.inaf.ia2.gms.model.request.MemberRequest;
+import it.inaf.ia2.gms.model.response.PaginatedData;
 import it.inaf.ia2.gms.model.Permission;
 import it.inaf.ia2.gms.model.RapUser;
-import it.inaf.ia2.gms.model.RemoveMemberRequest;
+import it.inaf.ia2.gms.model.request.RemoveMemberRequest;
+import it.inaf.ia2.gms.model.request.TabRequest;
 import it.inaf.ia2.gms.persistence.model.GroupEntity;
 import it.inaf.ia2.gms.service.GroupsService;
 import it.inaf.ia2.gms.service.MembersService;
@@ -19,6 +20,7 @@ import org.springframework.http.HttpStatus;
 import org.springframework.http.MediaType;
 import org.springframework.http.ResponseEntity;
 import org.springframework.web.bind.annotation.DeleteMapping;
+import org.springframework.web.bind.annotation.GetMapping;
 import org.springframework.web.bind.annotation.PostMapping;
 import org.springframework.web.bind.annotation.RequestBody;
 import org.springframework.web.bind.annotation.RestController;
@@ -38,6 +40,22 @@ public class MembersController {
     @Autowired
     private MembersService membersService;
 
+    @GetMapping(value = "/members", produces = MediaType.APPLICATION_JSON_UTF8_VALUE)
+    public ResponseEntity<PaginatedData<RapUser>> getMembersTab(TabRequest request) {
+
+        GroupEntity group = groupsService.getGroupById(request.getGroupId());
+        Permission currentNodePermissions = permissionsService.getUserPermissionForGroup(group, session.getUserId());
+
+        if (currentNodePermissions == Permission.TRAVERSE) {
+            throw new UnauthorizedException("You have not the permission to view members");
+        }
+
+        List<RapUser> members = membersService.getMembers(group.getId());
+        PaginatedData<RapUser> membersPanel = new PaginatedData<>(members, request.getPaginatorPage(), request.getPaginatorPageSize());
+
+        return ResponseEntity.ok(membersPanel);
+    }
+
     @PostMapping(value = "/member", consumes = MediaType.APPLICATION_JSON_UTF8_VALUE, produces = MediaType.APPLICATION_JSON_UTF8_VALUE)
     public ResponseEntity<PaginatedData<RapUser>> addMember(@Valid @RequestBody AddMemberRequest request) {
 
diff --git a/gms/src/main/java/it/inaf/ia2/gms/controller/PermissionsController.java b/gms/src/main/java/it/inaf/ia2/gms/controller/PermissionsController.java
index cd9ba1e87af24c08fe220cacb420f04fca4e115a..8d011d60e143f833445387f06233f876e959b6d9 100644
--- a/gms/src/main/java/it/inaf/ia2/gms/controller/PermissionsController.java
+++ b/gms/src/main/java/it/inaf/ia2/gms/controller/PermissionsController.java
@@ -2,12 +2,13 @@ package it.inaf.ia2.gms.controller;
 
 import it.inaf.ia2.gms.authn.SessionData;
 import it.inaf.ia2.gms.exception.UnauthorizedException;
-import it.inaf.ia2.gms.model.AddPermissionRequest;
-import it.inaf.ia2.gms.model.MemberRequest;
-import it.inaf.ia2.gms.model.PaginatedData;
-import it.inaf.ia2.gms.model.PaginatedModelRequest;
+import it.inaf.ia2.gms.model.request.AddPermissionRequest;
+import it.inaf.ia2.gms.model.request.MemberRequest;
+import it.inaf.ia2.gms.model.response.PaginatedData;
+import it.inaf.ia2.gms.model.request.PaginatedModelRequest;
 import it.inaf.ia2.gms.model.Permission;
 import it.inaf.ia2.gms.model.UserPermission;
+import it.inaf.ia2.gms.model.request.TabRequest;
 import it.inaf.ia2.gms.persistence.model.GroupEntity;
 import it.inaf.ia2.gms.service.GroupsService;
 import it.inaf.ia2.gms.service.PermissionsService;
@@ -38,7 +39,23 @@ public class PermissionsController {
     @Autowired
     private PermissionsService permissionsService;
 
-    @GetMapping(value = "/permission")
+    @GetMapping(value = "/permissions", produces = MediaType.APPLICATION_JSON_UTF8_VALUE)
+    public ResponseEntity<PaginatedData<UserPermission>> getPermissionsTab(TabRequest request) {
+
+        GroupEntity group = groupsService.getGroupById(request.getGroupId());
+        Permission currentNodePermissions = permissionsService.getUserPermissionForGroup(group, session.getUserId());
+
+        if (currentNodePermissions != Permission.ADMIN) {
+            throw new UnauthorizedException("Only administrators can see the permissions");
+        }
+
+        List<UserPermission> permissions = permissionsService.getAllPermissions(group);
+        PaginatedData<UserPermission> permissionsPanel = new PaginatedData<>(permissions, request.getPaginatorPage(), request.getPaginatorPageSize());
+
+        return ResponseEntity.ok(permissionsPanel);
+    }
+
+    @GetMapping(value = "/permission", produces = MediaType.APPLICATION_JSON_UTF8_VALUE)
     public ResponseEntity<Map<String, Permission>> getUserPermission(@RequestParam("groupId") String groupId, @RequestParam("userId") String userId) {
 
         GroupEntity group = groupsService.getGroupById(groupId);
diff --git a/gms/src/main/java/it/inaf/ia2/gms/controller/WebServiceController.java b/gms/src/main/java/it/inaf/ia2/gms/controller/WebServiceController.java
index b57df946d7a6ba6a52d06a5ebb4ac5cfda8d6c1d..2992f7907c98a177e5ffd02fffe68b4432e54006 100644
--- a/gms/src/main/java/it/inaf/ia2/gms/controller/WebServiceController.java
+++ b/gms/src/main/java/it/inaf/ia2/gms/controller/WebServiceController.java
@@ -1,9 +1,8 @@
 package it.inaf.ia2.gms.controller;
 
 import it.inaf.ia2.gms.exception.BadRequestException;
-import it.inaf.ia2.gms.model.AddMemberWsRequest;
-import it.inaf.ia2.gms.model.AddPermissionWsRequest;
-import it.inaf.ia2.gms.model.Permission;
+import it.inaf.ia2.gms.model.request.AddMemberWsRequest;
+import it.inaf.ia2.gms.model.request.AddPermissionWsRequest;
 import it.inaf.ia2.gms.model.PrepareToJoinRequest;
 import it.inaf.ia2.gms.persistence.model.GroupEntity;
 import it.inaf.ia2.gms.persistence.model.MembershipEntity;
diff --git a/gms/src/main/java/it/inaf/ia2/gms/model/GroupsModelRequest.java b/gms/src/main/java/it/inaf/ia2/gms/model/GroupsModelRequest.java
deleted file mode 100644
index 5c7a393ce19c8420069bc5b00f256b3f723bbb31..0000000000000000000000000000000000000000
--- a/gms/src/main/java/it/inaf/ia2/gms/model/GroupsModelRequest.java
+++ /dev/null
@@ -1,39 +0,0 @@
-package it.inaf.ia2.gms.model;
-
-import javax.validation.constraints.NotNull;
-
-public class GroupsModelRequest extends PaginatedModelRequest {
-
-    @NotNull
-    private String groupId;
-
-    @NotNull
-    private String tab;
-
-    @NotNull
-    private String page;
-
-    public String getGroupId() {
-        return groupId;
-    }
-
-    public void setGroupId(String groupId) {
-        this.groupId = groupId;
-    }
-
-    public String getTab() {
-        return tab;
-    }
-
-    public void setTab(String tab) {
-        this.tab = tab;
-    }
-
-    public String getPage() {
-        return page;
-    }
-
-    public void setPage(String page) {
-        this.page = page;
-    }
-}
diff --git a/gms/src/main/java/it/inaf/ia2/gms/model/CreateGroupRequest.java b/gms/src/main/java/it/inaf/ia2/gms/model/request/AddGroupRequest.java
similarity index 83%
rename from gms/src/main/java/it/inaf/ia2/gms/model/CreateGroupRequest.java
rename to gms/src/main/java/it/inaf/ia2/gms/model/request/AddGroupRequest.java
index d13ab80d4320bd1783f3c5e30a21783d97a351b0..3aeeb7fabef1fc4bc67b4a633722bc6b2576df91 100644
--- a/gms/src/main/java/it/inaf/ia2/gms/model/CreateGroupRequest.java
+++ b/gms/src/main/java/it/inaf/ia2/gms/model/request/AddGroupRequest.java
@@ -1,8 +1,8 @@
-package it.inaf.ia2.gms.model;
+package it.inaf.ia2.gms.model.request;
 
 import javax.validation.constraints.NotEmpty;
 
-public class CreateGroupRequest extends PaginatedModelRequest {
+public class AddGroupRequest extends PaginatedModelRequest {
 
     @NotEmpty
     private String parentGroupId;
diff --git a/gms/src/main/java/it/inaf/ia2/gms/model/AddMemberRequest.java b/gms/src/main/java/it/inaf/ia2/gms/model/request/AddMemberRequest.java
similarity index 86%
rename from gms/src/main/java/it/inaf/ia2/gms/model/AddMemberRequest.java
rename to gms/src/main/java/it/inaf/ia2/gms/model/request/AddMemberRequest.java
index 6f55c0af85c34633e0bea6397e68483f5c0e4513..14d24eda556cb6a3624c51de867e51bbd7117493 100644
--- a/gms/src/main/java/it/inaf/ia2/gms/model/AddMemberRequest.java
+++ b/gms/src/main/java/it/inaf/ia2/gms/model/request/AddMemberRequest.java
@@ -1,4 +1,6 @@
-package it.inaf.ia2.gms.model;
+package it.inaf.ia2.gms.model.request;
+
+import it.inaf.ia2.gms.model.Permission;
 
 public class AddMemberRequest extends MemberRequest {
 
diff --git a/gms/src/main/java/it/inaf/ia2/gms/model/AddMemberWsRequest.java b/gms/src/main/java/it/inaf/ia2/gms/model/request/AddMemberWsRequest.java
similarity index 91%
rename from gms/src/main/java/it/inaf/ia2/gms/model/AddMemberWsRequest.java
rename to gms/src/main/java/it/inaf/ia2/gms/model/request/AddMemberWsRequest.java
index cf698046f6a6c08b040a2ded9546f83aa6052069..72667392213b3ffb4aea0533cdfedda0e9c31cc4 100644
--- a/gms/src/main/java/it/inaf/ia2/gms/model/AddMemberWsRequest.java
+++ b/gms/src/main/java/it/inaf/ia2/gms/model/request/AddMemberWsRequest.java
@@ -1,4 +1,4 @@
-package it.inaf.ia2.gms.model;
+package it.inaf.ia2.gms.model.request;
 
 import java.util.List;
 
diff --git a/gms/src/main/java/it/inaf/ia2/gms/model/AddPermissionRequest.java b/gms/src/main/java/it/inaf/ia2/gms/model/request/AddPermissionRequest.java
similarity index 90%
rename from gms/src/main/java/it/inaf/ia2/gms/model/AddPermissionRequest.java
rename to gms/src/main/java/it/inaf/ia2/gms/model/request/AddPermissionRequest.java
index e4b2037e6eed7a8609c90f7df18b70d0e9b5b3bd..c10ae5f01a90bb2482a35d596047e5265a2f4ba8 100644
--- a/gms/src/main/java/it/inaf/ia2/gms/model/AddPermissionRequest.java
+++ b/gms/src/main/java/it/inaf/ia2/gms/model/request/AddPermissionRequest.java
@@ -1,5 +1,6 @@
-package it.inaf.ia2.gms.model;
+package it.inaf.ia2.gms.model.request;
 
+import it.inaf.ia2.gms.model.Permission;
 import javax.validation.constraints.NotEmpty;
 import javax.validation.constraints.NotNull;
 
diff --git a/gms/src/main/java/it/inaf/ia2/gms/model/AddPermissionWsRequest.java b/gms/src/main/java/it/inaf/ia2/gms/model/request/AddPermissionWsRequest.java
similarity index 90%
rename from gms/src/main/java/it/inaf/ia2/gms/model/AddPermissionWsRequest.java
rename to gms/src/main/java/it/inaf/ia2/gms/model/request/AddPermissionWsRequest.java
index 6e45d073680706fd537ba0f7ec5736fc8911f045..e8a4a17be0c023ad54b168bc19bc67d8d3b8e4ab 100644
--- a/gms/src/main/java/it/inaf/ia2/gms/model/AddPermissionWsRequest.java
+++ b/gms/src/main/java/it/inaf/ia2/gms/model/request/AddPermissionWsRequest.java
@@ -1,5 +1,6 @@
-package it.inaf.ia2.gms.model;
+package it.inaf.ia2.gms.model.request;
 
+import it.inaf.ia2.gms.model.Permission;
 import java.util.List;
 import javax.validation.constraints.NotEmpty;
 import javax.validation.constraints.NotNull;
diff --git a/gms/src/main/java/it/inaf/ia2/gms/model/MemberRequest.java b/gms/src/main/java/it/inaf/ia2/gms/model/request/MemberRequest.java
similarity index 92%
rename from gms/src/main/java/it/inaf/ia2/gms/model/MemberRequest.java
rename to gms/src/main/java/it/inaf/ia2/gms/model/request/MemberRequest.java
index 20d4873b3cc8dd9ee86482ceaadc6cecd593853a..de6d2c89dc5eb5272923afbe47b82318111f7ae7 100644
--- a/gms/src/main/java/it/inaf/ia2/gms/model/MemberRequest.java
+++ b/gms/src/main/java/it/inaf/ia2/gms/model/request/MemberRequest.java
@@ -1,4 +1,4 @@
-package it.inaf.ia2.gms.model;
+package it.inaf.ia2.gms.model.request;
 
 import javax.validation.constraints.NotEmpty;
 
diff --git a/gms/src/main/java/it/inaf/ia2/gms/model/PaginatedModelRequest.java b/gms/src/main/java/it/inaf/ia2/gms/model/request/PaginatedModelRequest.java
similarity index 93%
rename from gms/src/main/java/it/inaf/ia2/gms/model/PaginatedModelRequest.java
rename to gms/src/main/java/it/inaf/ia2/gms/model/request/PaginatedModelRequest.java
index 371b90b548ab9794e7851f18689b7f37d4e56717..7910d69f1f50bd9d2bc1855902c073ebc35134bb 100644
--- a/gms/src/main/java/it/inaf/ia2/gms/model/PaginatedModelRequest.java
+++ b/gms/src/main/java/it/inaf/ia2/gms/model/request/PaginatedModelRequest.java
@@ -1,4 +1,4 @@
-package it.inaf.ia2.gms.model;
+package it.inaf.ia2.gms.model.request;
 
 import javax.validation.constraints.Min;
 
diff --git a/gms/src/main/java/it/inaf/ia2/gms/model/RemoveMemberRequest.java b/gms/src/main/java/it/inaf/ia2/gms/model/request/RemoveMemberRequest.java
similarity index 89%
rename from gms/src/main/java/it/inaf/ia2/gms/model/RemoveMemberRequest.java
rename to gms/src/main/java/it/inaf/ia2/gms/model/request/RemoveMemberRequest.java
index ff2251574aee036bbc5ceddb1358b0cdbfa2fab1..820a2b8538339405595a6765ac590f3ae3a57f67 100644
--- a/gms/src/main/java/it/inaf/ia2/gms/model/RemoveMemberRequest.java
+++ b/gms/src/main/java/it/inaf/ia2/gms/model/request/RemoveMemberRequest.java
@@ -1,4 +1,4 @@
-package it.inaf.ia2.gms.model;
+package it.inaf.ia2.gms.model.request;
 
 public class RemoveMemberRequest extends MemberRequest {
 
diff --git a/gms/src/main/java/it/inaf/ia2/gms/model/RenameGroupRequest.java b/gms/src/main/java/it/inaf/ia2/gms/model/request/RenameGroupRequest.java
similarity index 91%
rename from gms/src/main/java/it/inaf/ia2/gms/model/RenameGroupRequest.java
rename to gms/src/main/java/it/inaf/ia2/gms/model/request/RenameGroupRequest.java
index 90feff7ea368b6932de9f903140d74a18f30bc17..1112b444430724037c1254bed01e7e68191c0a2a 100644
--- a/gms/src/main/java/it/inaf/ia2/gms/model/RenameGroupRequest.java
+++ b/gms/src/main/java/it/inaf/ia2/gms/model/request/RenameGroupRequest.java
@@ -1,4 +1,4 @@
-package it.inaf.ia2.gms.model;
+package it.inaf.ia2.gms.model.request;
 
 import javax.validation.constraints.NotNull;
 import javax.validation.constraints.Size;
diff --git a/gms/src/main/java/it/inaf/ia2/gms/model/request/TabRequest.java b/gms/src/main/java/it/inaf/ia2/gms/model/request/TabRequest.java
new file mode 100644
index 0000000000000000000000000000000000000000..e2d913baa757b01dfa9ae0d54ae5bbbce0b5107a
--- /dev/null
+++ b/gms/src/main/java/it/inaf/ia2/gms/model/request/TabRequest.java
@@ -0,0 +1,17 @@
+package it.inaf.ia2.gms.model.request;
+
+import javax.validation.constraints.NotNull;
+
+public class TabRequest extends PaginatedModelRequest {
+
+    @NotNull
+    private String groupId;
+
+    public String getGroupId() {
+        return groupId;
+    }
+
+    public void setGroupId(String groupId) {
+        this.groupId = groupId;
+    }
+}
diff --git a/gms/src/main/java/it/inaf/ia2/gms/model/BaseModelResponse.java b/gms/src/main/java/it/inaf/ia2/gms/model/response/BaseModelResponse.java
similarity index 89%
rename from gms/src/main/java/it/inaf/ia2/gms/model/BaseModelResponse.java
rename to gms/src/main/java/it/inaf/ia2/gms/model/response/BaseModelResponse.java
index b8999c5fdaf278aa89e49283198f84b00290e3c4..1988d52ec0bca526374f516eccc8ac48c4a78f73 100644
--- a/gms/src/main/java/it/inaf/ia2/gms/model/BaseModelResponse.java
+++ b/gms/src/main/java/it/inaf/ia2/gms/model/response/BaseModelResponse.java
@@ -1,4 +1,4 @@
-package it.inaf.ia2.gms.model;
+package it.inaf.ia2.gms.model.response;
 
 public abstract class BaseModelResponse {
 
diff --git a/gms/src/main/java/it/inaf/ia2/gms/model/GroupsModelResponse.java b/gms/src/main/java/it/inaf/ia2/gms/model/response/GroupsTabResponse.java
similarity index 54%
rename from gms/src/main/java/it/inaf/ia2/gms/model/GroupsModelResponse.java
rename to gms/src/main/java/it/inaf/ia2/gms/model/response/GroupsTabResponse.java
index 25cef046de7dc4e9e5ac878cc3156e61063e23e3..4df4cb508c2acb80ba4e5fa5dfd059e62298b4cc 100644
--- a/gms/src/main/java/it/inaf/ia2/gms/model/GroupsModelResponse.java
+++ b/gms/src/main/java/it/inaf/ia2/gms/model/response/GroupsTabResponse.java
@@ -1,13 +1,14 @@
-package it.inaf.ia2.gms.model;
+package it.inaf.ia2.gms.model.response;
 
+import it.inaf.ia2.gms.model.GroupBreadcrumb;
+import it.inaf.ia2.gms.model.GroupNode;
+import it.inaf.ia2.gms.model.Permission;
 import java.util.List;
 
-public class GroupsModelResponse extends BaseModelResponse {
+public class GroupsTabResponse {
 
     private List<GroupBreadcrumb> breadcrumbs;
     private PaginatedData<GroupNode> groupsPanel;
-    private PaginatedData<RapUser> membersPanel;
-    private PaginatedData<UserPermission> permissionsPanel;
     // current group permissions
     private Permission permission;
 
@@ -27,22 +28,6 @@ public class GroupsModelResponse extends BaseModelResponse {
         this.groupsPanel = groupsPanel;
     }
 
-    public PaginatedData<RapUser> getMembersPanel() {
-        return membersPanel;
-    }
-
-    public void setMembersPanel(PaginatedData<RapUser> membersPanel) {
-        this.membersPanel = membersPanel;
-    }
-
-    public PaginatedData<UserPermission> getPermissionsPanel() {
-        return permissionsPanel;
-    }
-
-    public void setPermissionsPanel(PaginatedData<UserPermission> permissionsPanel) {
-        this.permissionsPanel = permissionsPanel;
-    }
-
     public Permission getPermission() {
         return permission;
     }
diff --git a/gms/src/main/java/it/inaf/ia2/gms/model/response/HomePageResponse.java b/gms/src/main/java/it/inaf/ia2/gms/model/response/HomePageResponse.java
new file mode 100644
index 0000000000000000000000000000000000000000..418e46559e3b25b2d6253bc8c7d033b67c4f6e27
--- /dev/null
+++ b/gms/src/main/java/it/inaf/ia2/gms/model/response/HomePageResponse.java
@@ -0,0 +1,14 @@
+package it.inaf.ia2.gms.model.response;
+
+public class HomePageResponse extends GroupsTabResponse {
+
+    private String user;
+
+    public String getUser() {
+        return user;
+    }
+
+    public void setUser(String user) {
+        this.user = user;
+    }
+}
diff --git a/gms/src/main/java/it/inaf/ia2/gms/model/PaginatedData.java b/gms/src/main/java/it/inaf/ia2/gms/model/response/PaginatedData.java
similarity index 98%
rename from gms/src/main/java/it/inaf/ia2/gms/model/PaginatedData.java
rename to gms/src/main/java/it/inaf/ia2/gms/model/response/PaginatedData.java
index 0e61eb13b1760dc562a6b9ae18913dc1ef0ce5f3..78f917a6bf76b98b8615a91706534f0014bf6892 100644
--- a/gms/src/main/java/it/inaf/ia2/gms/model/PaginatedData.java
+++ b/gms/src/main/java/it/inaf/ia2/gms/model/response/PaginatedData.java
@@ -1,4 +1,4 @@
-package it.inaf.ia2.gms.model;
+package it.inaf.ia2.gms.model.response;
 
 import java.util.ArrayList;
 import java.util.List;
diff --git a/gms/src/main/java/it/inaf/ia2/gms/service/GroupsModelBuilder.java b/gms/src/main/java/it/inaf/ia2/gms/service/GroupsModelBuilder.java
deleted file mode 100644
index a0577470119ad1e1571e531be8713011ea04ce76..0000000000000000000000000000000000000000
--- a/gms/src/main/java/it/inaf/ia2/gms/service/GroupsModelBuilder.java
+++ /dev/null
@@ -1,62 +0,0 @@
-package it.inaf.ia2.gms.service;
-
-import it.inaf.ia2.gms.model.GroupsModelRequest;
-import it.inaf.ia2.gms.model.GroupsModelResponse;
-import it.inaf.ia2.gms.model.PaginatedData;
-import it.inaf.ia2.gms.model.Permission;
-import it.inaf.ia2.gms.model.RapUser;
-import it.inaf.ia2.gms.model.UserPermission;
-import it.inaf.ia2.gms.persistence.model.GroupEntity;
-import java.util.List;
-import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.stereotype.Component;
-
-@Component
-public class GroupsModelBuilder {
-
-    @Autowired
-    private GroupsService groupsService;
-
-    @Autowired
-    private GroupsTreeBuilder groupsTreeBuilder;
-
-    @Autowired
-    private MembersService membersService;
-
-    @Autowired
-    private PermissionsService permissionsService;
-
-    public GroupsModelResponse getGroupsModel(GroupsModelRequest request, String userId) {
-
-        GroupEntity group = groupsService.getGroupById(request.getGroupId());
-
-        GroupsModelResponse response = new GroupsModelResponse();
-
-        response.setPage("groups");
-
-        response.setBreadcrumbs(groupsService.getBreadcrumbs(group.getPath()));
-
-        Permission currentNodePermissions = permissionsService.getUserPermissionForGroup(group, userId);
-        response.setPermission(currentNodePermissions);
-
-        switch (request.getTab()) {
-            case "groups":
-                response.setGroupsPanel(groupsTreeBuilder.listSubGroups(group.getId(), userId, request));
-                break;
-            case "members":
-                if (currentNodePermissions != Permission.TRAVERSE) {
-                    List<RapUser> members = membersService.getMembers(group.getId());
-                    response.setMembersPanel(new PaginatedData<>(members, request.getPaginatorPage(), request.getPaginatorPageSize()));
-                }
-                break;
-            case "permissions":
-                if (currentNodePermissions == Permission.ADMIN) {
-                    List<UserPermission> permissions = permissionsService.getAllPermissions(group);
-                    response.setPermissionsPanel(new PaginatedData<>(permissions, request.getPaginatorPage(), request.getPaginatorPageSize()));
-                }
-                break;
-        }
-
-        return response;
-    }
-}
diff --git a/gms/src/main/java/it/inaf/ia2/gms/service/GroupsTreeBuilder.java b/gms/src/main/java/it/inaf/ia2/gms/service/GroupsTreeBuilder.java
index 280d5eef731d75a6388cdd423ab0d0874290a300..665e90b471df90e8b8e08f9aae6b151e448f1d24 100644
--- a/gms/src/main/java/it/inaf/ia2/gms/service/GroupsTreeBuilder.java
+++ b/gms/src/main/java/it/inaf/ia2/gms/service/GroupsTreeBuilder.java
@@ -2,8 +2,8 @@ package it.inaf.ia2.gms.service;
 
 import it.inaf.ia2.gms.exception.BadRequestException;
 import it.inaf.ia2.gms.model.GroupNode;
-import it.inaf.ia2.gms.model.PaginatedData;
-import it.inaf.ia2.gms.model.PaginatedModelRequest;
+import it.inaf.ia2.gms.model.response.PaginatedData;
+import it.inaf.ia2.gms.model.request.PaginatedModelRequest;
 import it.inaf.ia2.gms.persistence.GroupsDAO;
 import it.inaf.ia2.gms.persistence.PermissionsDAO;
 import it.inaf.ia2.gms.persistence.model.GroupEntity;
diff --git a/gms/src/test/java/it/inaf/ia2/gms/controller/GroupsControllerTest.java b/gms/src/test/java/it/inaf/ia2/gms/controller/GroupsControllerTest.java
index 37e7b92159b932e2a14bf589bbfe6a5461f43702..f1acf43729643b34d029933b7a969ff1edf8a7d7 100644
--- a/gms/src/test/java/it/inaf/ia2/gms/controller/GroupsControllerTest.java
+++ b/gms/src/test/java/it/inaf/ia2/gms/controller/GroupsControllerTest.java
@@ -1,23 +1,30 @@
 package it.inaf.ia2.gms.controller;
 
 import it.inaf.ia2.gms.authn.SessionData;
-import it.inaf.ia2.gms.model.GroupsModelRequest;
-import it.inaf.ia2.gms.model.GroupsModelResponse;
-import it.inaf.ia2.gms.service.GroupsModelBuilder;
-import static org.junit.Assert.assertEquals;
+import it.inaf.ia2.gms.model.GroupNode;
+import it.inaf.ia2.gms.model.Permission;
+import it.inaf.ia2.gms.model.response.PaginatedData;
+import it.inaf.ia2.gms.persistence.model.GroupEntity;
+import it.inaf.ia2.gms.service.GroupsService;
+import it.inaf.ia2.gms.service.GroupsTreeBuilder;
+import it.inaf.ia2.gms.service.PermissionsService;
+import java.util.ArrayList;
+import static org.hamcrest.CoreMatchers.is;
+import static org.hamcrest.CoreMatchers.notNullValue;
 import org.junit.Before;
 import org.junit.Test;
 import org.junit.runner.RunWith;
-import org.mockito.ArgumentCaptor;
 import static org.mockito.ArgumentMatchers.any;
+import static org.mockito.ArgumentMatchers.eq;
 import org.mockito.InjectMocks;
 import org.mockito.Mock;
-import static org.mockito.Mockito.verify;
 import static org.mockito.Mockito.when;
+import org.mockito.Spy;
 import org.mockito.junit.MockitoJUnitRunner;
 import org.springframework.test.web.servlet.MockMvc;
 import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
 import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get;
+import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.jsonPath;
 import org.springframework.test.web.servlet.setup.MockMvcBuilders;
 
 @RunWith(MockitoJUnitRunner.class)
@@ -27,7 +34,17 @@ public class GroupsControllerTest {
     private SessionData session;
 
     @Mock
-    private GroupsModelBuilder groupsModelService;
+    private GroupsService groupsService;
+
+    @Mock
+    private PermissionsService permissionsService;
+
+    @Mock
+    private GroupsTreeBuilder groupsTreeBuilder;
+
+    @Spy
+    @InjectMocks
+    private GroupsTabResponseBuilder groupsTabResponseBuilder;
 
     @InjectMocks
     private GroupsController controller;
@@ -42,21 +59,25 @@ public class GroupsControllerTest {
     @Test
     public void testGetGroups() throws Exception {
 
-        GroupsModelResponse response = new GroupsModelResponse();
+        when(session.getUserId()).thenReturn("admin_id");
+
+        GroupEntity root = new GroupEntity();
+        root.setId("ROOT");
+        root.setName("ROOT");
+        root.setPath("");
 
-        when(groupsModelService.getGroupsModel(any(), any()))
-                .thenReturn(response);
+        when(groupsService.getGroupById(eq("ROOT"))).thenReturn(root);
 
-        mockMvc.perform(get("/groups?groupId=ROOT&tab=groups&paginatorPageSize=20&paginatorPage=1&page=main"))
-                .andExpect(status().isOk());
+        when(permissionsService.getUserPermissionForGroup(eq(root), eq("admin_id")))
+                .thenReturn(Permission.ADMIN);
 
-        ArgumentCaptor<GroupsModelRequest> requestCaptor = ArgumentCaptor.forClass(GroupsModelRequest.class);
-        verify(groupsModelService).getGroupsModel(requestCaptor.capture(), any());
-        GroupsModelRequest request = requestCaptor.getValue();
+        PaginatedData<GroupNode> groupsPanel = new PaginatedData<>(new ArrayList<>(), 1, 10);
+        when(groupsTreeBuilder.listSubGroups(eq("ROOT"), eq("admin_id"), any())).thenReturn(groupsPanel);
 
-        assertEquals("ROOT", request.getGroupId());
-        assertEquals("groups", request.getTab());
-        assertEquals(1, request.getPaginatorPage());
-        assertEquals(20, request.getPaginatorPageSize());
+        mockMvc.perform(get("/groups?groupId=ROOT&paginatorPageSize=20&paginatorPage=1"))
+                .andExpect(status().isOk())
+                .andExpect(jsonPath("$.breadcrumbs", notNullValue()))
+                .andExpect(jsonPath("$.groupsPanel", notNullValue()))
+                .andExpect(jsonPath("$.permission", is("ADMIN")));
     }
 }
diff --git a/gms/src/test/java/it/inaf/ia2/gms/controller/HomePageControllerTest.java b/gms/src/test/java/it/inaf/ia2/gms/controller/HomePageControllerTest.java
new file mode 100644
index 0000000000000000000000000000000000000000..6f74fae5b52c21fbf1f96e2e7c59bd8e3421b513
--- /dev/null
+++ b/gms/src/test/java/it/inaf/ia2/gms/controller/HomePageControllerTest.java
@@ -0,0 +1,50 @@
+package it.inaf.ia2.gms.controller;
+
+import it.inaf.ia2.gms.authn.SessionData;
+import it.inaf.ia2.gms.model.response.GroupsTabResponse;
+import static org.hamcrest.CoreMatchers.notNullValue;
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import static org.mockito.ArgumentMatchers.any;
+import org.mockito.InjectMocks;
+import org.mockito.Mock;
+import static org.mockito.Mockito.when;
+import org.mockito.junit.MockitoJUnitRunner;
+import org.springframework.test.web.servlet.MockMvc;
+import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get;
+import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.jsonPath;
+import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
+import org.springframework.test.web.servlet.setup.MockMvcBuilders;
+
+@RunWith(MockitoJUnitRunner.class)
+public class HomePageControllerTest {
+
+    @Mock
+    private SessionData session;
+
+    @Mock
+    private GroupsTabResponseBuilder groupsTabResponseBuilder;
+
+    @InjectMocks
+    private HomePageController controller;
+
+    private MockMvc mockMvc;
+
+    @Before
+    public void init() {
+        mockMvc = MockMvcBuilders.standaloneSetup(controller).build();
+    }
+
+    @Test
+    public void testGetHomePageModel() throws Exception {
+
+        when(session.getUserId()).thenReturn("admin_id");
+
+        when(groupsTabResponseBuilder.getGroupsTab(any())).thenReturn(new GroupsTabResponse());
+
+        mockMvc.perform(get("/home?groupId=ROOT&paginatorPageSize=20&paginatorPage=1"))
+                .andExpect(status().isOk())
+                .andExpect(jsonPath("$.user", notNullValue()));
+    }
+}
diff --git a/gms/src/test/java/it/inaf/ia2/gms/controller/MembersControllerTest.java b/gms/src/test/java/it/inaf/ia2/gms/controller/MembersControllerTest.java
index b18fc5a790db88b991167e13b1fd91b667ba8250..968bf92d2f8f8ed0658f7acf40c3a8419e24a69f 100644
--- a/gms/src/test/java/it/inaf/ia2/gms/controller/MembersControllerTest.java
+++ b/gms/src/test/java/it/inaf/ia2/gms/controller/MembersControllerTest.java
@@ -2,7 +2,7 @@ package it.inaf.ia2.gms.controller;
 
 import com.fasterxml.jackson.databind.ObjectMapper;
 import it.inaf.ia2.gms.authn.SessionData;
-import it.inaf.ia2.gms.model.AddMemberRequest;
+import it.inaf.ia2.gms.model.request.AddMemberRequest;
 import it.inaf.ia2.gms.model.Permission;
 import it.inaf.ia2.gms.persistence.model.GroupEntity;
 import it.inaf.ia2.gms.service.GroupsService;
diff --git a/gms/src/test/java/it/inaf/ia2/gms/controller/PermissionsControllerTest.java b/gms/src/test/java/it/inaf/ia2/gms/controller/PermissionsControllerTest.java
index 4b635ebb2fd92e59bfa18364fd18136cc11e31e9..b309bf13d850ecf1f5c1297d591923677645aa7e 100644
--- a/gms/src/test/java/it/inaf/ia2/gms/controller/PermissionsControllerTest.java
+++ b/gms/src/test/java/it/inaf/ia2/gms/controller/PermissionsControllerTest.java
@@ -3,7 +3,7 @@ package it.inaf.ia2.gms.controller;
 import com.fasterxml.jackson.databind.ObjectMapper;
 import it.inaf.ia2.gms.authn.SessionData;
 import it.inaf.ia2.gms.model.Permission;
-import it.inaf.ia2.gms.model.AddPermissionRequest;
+import it.inaf.ia2.gms.model.request.AddPermissionRequest;
 import it.inaf.ia2.gms.persistence.model.GroupEntity;
 import it.inaf.ia2.gms.service.GroupsService;
 import it.inaf.ia2.gms.service.PermissionsService;
diff --git a/gms/src/test/java/it/inaf/ia2/gms/controller/WebServiceControllerTest.java b/gms/src/test/java/it/inaf/ia2/gms/controller/WebServiceControllerTest.java
index 422b915e2a0a56c64bcc45bdca5970fcfea4bd5d..695bc777bc4757edc8a5e214967d3ac42a124375 100644
--- a/gms/src/test/java/it/inaf/ia2/gms/controller/WebServiceControllerTest.java
+++ b/gms/src/test/java/it/inaf/ia2/gms/controller/WebServiceControllerTest.java
@@ -1,8 +1,8 @@
 package it.inaf.ia2.gms.controller;
 
 import com.fasterxml.jackson.databind.ObjectMapper;
-import it.inaf.ia2.gms.model.AddMemberWsRequest;
-import it.inaf.ia2.gms.model.AddPermissionWsRequest;
+import it.inaf.ia2.gms.model.request.AddMemberWsRequest;
+import it.inaf.ia2.gms.model.request.AddPermissionWsRequest;
 import it.inaf.ia2.gms.model.Permission;
 import it.inaf.ia2.gms.model.PrepareToJoinRequest;
 import it.inaf.ia2.gms.persistence.model.GroupEntity;
diff --git a/gms/src/test/java/it/inaf/ia2/gms/model/PaginatedDataTest.java b/gms/src/test/java/it/inaf/ia2/gms/model/PaginatedDataTest.java
index 79f2d9b0d5e6288a38b5521ef84f8667eab43446..173f7e0e6fc0c3eee21bc6257f5da6d083ecd107 100644
--- a/gms/src/test/java/it/inaf/ia2/gms/model/PaginatedDataTest.java
+++ b/gms/src/test/java/it/inaf/ia2/gms/model/PaginatedDataTest.java
@@ -1,5 +1,6 @@
 package it.inaf.ia2.gms.model;
 
+import it.inaf.ia2.gms.model.response.PaginatedData;
 import java.util.ArrayList;
 import java.util.List;
 import static org.junit.Assert.assertEquals;
diff --git a/gms/src/test/java/it/inaf/ia2/gms/persistence/NestedGroupsIntegrationTest.java b/gms/src/test/java/it/inaf/ia2/gms/persistence/NestedGroupsIntegrationTest.java
index 0b79415a8321b348afd5e4647a56e5b4e6f1dbcc..2ca372b54103f2b7b57a51ac78df9390fff08d61 100644
--- a/gms/src/test/java/it/inaf/ia2/gms/persistence/NestedGroupsIntegrationTest.java
+++ b/gms/src/test/java/it/inaf/ia2/gms/persistence/NestedGroupsIntegrationTest.java
@@ -3,7 +3,7 @@ package it.inaf.ia2.gms.persistence;
 import it.inaf.ia2.gms.DataSourceConfig;
 import it.inaf.ia2.gms.service.GroupsService;
 import it.inaf.ia2.gms.model.GroupNode;
-import it.inaf.ia2.gms.model.PaginatedModelRequest;
+import it.inaf.ia2.gms.model.request.PaginatedModelRequest;
 import it.inaf.ia2.gms.model.Permission;
 import it.inaf.ia2.gms.persistence.model.GroupEntity;
 import it.inaf.ia2.gms.persistence.model.PermissionEntity;