Index: /branches/amp_3_6_0_role/amp.spec
===================================================================
--- /branches/amp_3_6_0_role/amp.spec	(revision 2350)
+++ /branches/amp_3_6_0_role/amp.spec	(working copy)
@@ -1,5 +1,5 @@
 Name:           amp
-Version:        3.4.1.0
+Version:        3.6.0.1
 Release:        1%{?dist}
 Summary:        Array Management Platform 
 Group:          Development/Tools
Index: /branches/amp_3_6_0_role/extensions/auditing/webui/log_analysis/slb_service/slb/slb.controller.js
===================================================================
--- /branches/amp_3_6_0_role/extensions/auditing/webui/log_analysis/slb_service/slb/slb.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/extensions/auditing/webui/log_analysis/slb_service/slb/slb.controller.js	(working copy)
@@ -10,10 +10,11 @@
         'deviceService',
         'dashboardService',
         'localStorageService',
-        function ($scope, $rootScope, $state, $stateParams, $location, $uibModal,$filter, deviceService, dashboardService, localStorageService) {
+        'roleMgmtService',
+        function ($scope, $rootScope, $state, $stateParams, $location, $uibModal, $filter, deviceService, dashboardService, localStorageService, roleMgmtService) {
             $rootScope.title = 'SLB Service';
             var serviceViewModel = this;
-
+            $scope.role_info = localStorageService.getWebStorage('role_info');
             $scope.currentPageIndex = 1;
             $scope.pageSize = 20;
             $scope.onPageChange = function (newPage) {
@@ -26,7 +27,7 @@
                 if (serviceViewModel.serviceList === undefined) {
                     return true;
                 }
-                for(var i in serviceViewModel.all_loadings){
+                for (var i in serviceViewModel.all_loadings) {
                     if (!serviceViewModel.all_loadings[i]) {
                         return false;
                     }
@@ -38,7 +39,7 @@
                     serviceViewModel.host_list = undefined;
                     serviceViewModel.all_loadings = {};
                     serviceViewModel.serviceList = [];
-                    getServiceList ();
+                    getServiceList();
                 }
             }
             serviceViewModel.setDetail = function (device) {
@@ -51,52 +52,67 @@
             }
 
             var device_type_info = localStorageService.getWebStorage("device_type_info");
-            function getServiceList () {
-                deviceService
-                    .getDeviceList()
-                    .then(function(res){
-                        if (res&&res.status === 200) {
-                            serviceViewModel.host_list = res.data;
-                            serviceViewModel.serviceList = [];
-                            _.each(serviceViewModel.host_list, function(host) {
-                                serviceViewModel.all_loadings[host.name] = false;
-                                if (host.connection && device_type_info.ADC_TYPE_LIST.indexOf(host.type.toLowerCase()) != -1) {
-                                    dashboardService
-                                    .getAllVirtualService(host.id)
-                                    .then(function(res) {
-                                        serviceViewModel.all_loadings[host.name] = true;
-                                        if (res && res.status === 200 && res.data.VirtualService) {
-                                            _.each(res.data.VirtualService, function(data) {
-                                                // if (data.protocol == 'vlink') {
-                                                //     return;
-                                                // }
-                                                var tmp = {
-                                                    "name":data.service_name,
-                                                    "type":data.protocol,
-                                                    "device":host,
-                                                    "ip":data.vip
+
+            function getServiceList() {
+                serviceViewModel.serviceList = [];
+                roleMgmtService.getRoleDeviceGroupMapping($scope.role_info).then(function (res) {
+                    var device_type_info = localStorageService.getWebStorage("device_type_info");
+                    if (res && res.status === 200 && res.data instanceof Array) {
+                        let data = res.data;
+                        if (data.length > 1) {
+                            try {
+                                let deviceMap = data[1]['result'];
+                                let device_list = [];
+                                deviceMap.forEach(function (deviceGroup) {
+                                    deviceGroup['device_list'].forEach(function (device) {
+                                        device_list.push(device);
+                                    })
+                                })
+                                serviceViewModel.host_list = device_list;
+                                _.each(serviceViewModel.host_list, function (host) {
+                                    serviceViewModel.all_loadings[host.name] = false;
+                                    if (host.connection && device_type_info.ADC_TYPE_LIST.indexOf(host.type.toLowerCase()) !== -1) {
+                                        dashboardService
+                                            .getAllVirtualService(host.id)
+                                            .then(function (res) {
+                                                serviceViewModel.all_loadings[host.name] = true;
+                                                if (res && res.status === 200 && res.data.VirtualService) {
+                                                    _.each(res.data.VirtualService, function (data) {
+                                                        // if (data.protocol == 'vlink') {
+                                                        //     return;
+                                                        // }
+                                                        var tmp = {
+                                                            "name": data.service_name,
+                                                            "type": data.protocol,
+                                                            "device": host,
+                                                            "ip": data.vip
+                                                        }
+                                                        serviceViewModel.serviceList.push(tmp);
+                                                    });
+                                                } else {
+                                                    //error
                                                 }
-                                                serviceViewModel.serviceList.push(tmp);
                                             });
-                                        } else {
-                                            //error
-                                        }
-                                    });
-                                } else {
-                                    serviceViewModel.all_loadings[host.name] = true;
-                                }
-                            });
+                                    } else {
+                                        serviceViewModel.all_loadings[host.name] = true;
+                                    }
+                                });
+                            } catch (e) {
+                                console.error('Error getRoleDeviceGroupMapping returned error.' + e);
+                                serviceViewModel.serviceList = [];
+                            }
                         }
-                    }); 
+                    }
+                });
             }
 
             getServiceList();
 
             serviceViewModel.detail = function (item) {
                 var device_list = {
-                    device_list : item.device,
+                    device_list: item.device,
                     vs: item.name,
-                    vs_ip:item.ip
+                    vs_ip: item.ip
                 };
                 window.localStorage.__slbInfoDeviceList__ = JSON.stringify(device_list);
             };
Index: /branches/amp_3_6_0_role/extensions/auditing/webui/log_analysis/sslvpn_service/audit.service.js
===================================================================
--- /branches/amp_3_6_0_role/extensions/auditing/webui/log_analysis/sslvpn_service/audit.service.js	(revision 2350)
+++ /branches/amp_3_6_0_role/extensions/auditing/webui/log_analysis/sslvpn_service/audit.service.js	(working copy)
@@ -25,18 +25,14 @@
                 clearLog: clearLog
             };
 
-            function getUserList(startstamp, endstamp) {
+            function getUserList(startstamp, endstamp, remoteIPs=[]) {
                 var deferred = $q.defer();
                 var post_data = {
                     "size": 0,
                     "query": {
                         "bool": {
+                            "must": [{"terms": {"tag.remote_ip": remoteIPs}}],
                             "filter": [
-                                // {
-                                //     "match_phrase": {
-                                //         "tag.logid": { "query": "200050021" }
-                                //     }
-                                // },
                                 {
                                     "range": {
                                         "@timestamp": {
@@ -69,34 +65,13 @@
                             }
                         }
                     }
-                    // "aggs": {
-                    //     "host_list": {
-                    //         "terms": { "field": "tag.remote_ip","size":0, },
-                    //         "aggs": {
-                    //             "vsite_list": {
-                    //                 "terms": { "field": "vpn.site" },
-                    //                 "aggs": {
-                    //                     "user_list": {
-                    //                         "terms": {
-                    //                             "field": "vpn.user"
-                    //                         },
-                    //                         "aggs": {
-                    //                             "login_time": {
-                    //                                 "max": { "field": "@timestamp" }
-                    //                             }
-                    //                         }
-                    //                     }
-                    //                 }
-                    //             }
-                    //         }
-                    //     }
-                    // }
                 };
 
                 var post_data_login = {
                     "size": 0,
                     "query": {
                         "bool": {
+                            "must": [{"terms": {"tag.remote_ip": remoteIPs}}],
                             "filter": [
                                 {
                                     "match_phrase": {
@@ -148,7 +123,6 @@
                             _.each(result["data"]["aggregations"]["host_list"]["buckets"], function (host_data) {
                                 _.each(host_data["vsite_list"]["buckets"], function (vs_data) {
                                     _.each(vs_data["user_list"]["buckets"], function (user_data) {
-                                        // var last_login_time = new Date(user_data["login_time"]["value"]).format('yyyy-mm-dd HH:MM:ss');
                                         user_dict[host_data["key"] + '-' + vs_data["key"] + '-' + user_data["key"]] = {
                                             "host_name": host_data["key"],
                                             "vsite_name": vs_data["key"],
@@ -156,13 +130,6 @@
                                             "last_login_time": 'N/A',
                                             "last_login_timestamp": 0
                                         }
-                                        // res["data"].push({
-                                        //     "host_name": host_data["key"],
-                                        //     "vsite_name": vs_data["key"],
-                                        //     "user_name": user_data["key"],
-                                        //     "last_login_time": last_login_time,
-                                        //     "last_login_timestamp": user_data["login_time"]["value"]
-                                        // })
                                     });
                                 });
                             });
@@ -674,13 +641,14 @@
             function sort_by_times(a, b) {
                 return b.times - a.times;
             }
-            function getUserTopRanking(data) {
+            function getUserTopRanking(data, remoteIPs=[]) {
                 var post_data_l3 = {
                     "size": 0,
                     "query": {
                         "bool": {
                             "must": [
                                 { "term": { "tag.logid": "200055002" } },
+                                {"terms": {"tag.remote_ip": remoteIPs}},
                                 {
                                     "range": {
                                         "@timestamp": {
@@ -729,6 +697,7 @@
                         "bool": {
                             "must": [
                                 { "term": { "tag.logid": "200055002" } },
+                                {"terms": {"tag.remote_ip": remoteIPs}},
                                 {
                                     "range": {
                                         "@timestamp": {
@@ -771,6 +740,7 @@
                                 "bool": {
                                     "must": [
                                         { "term": { "tag.logid": "200050021" } },
+                                        {"terms": {"tag.remote_ip": remoteIPs}},
                                         {
                                             "range": {
                                                 "@timestamp": {
@@ -810,6 +780,7 @@
                             "filter": {
                                 "bool": {
                                     "must": [
+                                        {"terms": {"tag.remote_ip": remoteIPs}},
                                         {
                                             "range": {
                                                 "@timestamp": {
@@ -859,6 +830,7 @@
                                 "bool": {
                                     "must": [
                                         { "term": { "tag.logid": "200055002" } },
+                                        {"terms": {"tag.remote_ip": remoteIPs}},
                                         {
                                             "range": {
                                                 "@timestamp": {
@@ -905,6 +877,7 @@
                             "filter": {
                                 "bool": {
                                     "must": [
+                                        {"terms": {"tag.remote_ip": remoteIPs}},
                                         {
                                             "range": {
                                                 "@timestamp": {
@@ -945,6 +918,7 @@
                                 "bool": {
                                     "must": [
                                         { "term": { "tag.logid": "200002221" } },
+                                        {"terms": {"tag.remote_ip": remoteIPs}},
                                         {
                                             "range": {
                                                 "@timestamp": {
@@ -1223,12 +1197,13 @@
                 return deferred.promise;
             }
 
-            function getDeviceList(startstamp, endstamp) {
+            function getDeviceList(startstamp, endstamp, remoteIPs=[]) {
                 var deferred = $q.defer();
                 var post_data = {
                     "size": 0,
                     "query": {
                         "bool": {
+                            "must": [{"terms": {"tag.remote_ip": remoteIPs}}],
                             "filter": [
                                 {
                                     "match_phrase": {
Index: /branches/amp_3_6_0_role/extensions/auditing/webui/log_analysis/sslvpn_service/tabs/device/deviceList.controller.js
===================================================================
--- /branches/amp_3_6_0_role/extensions/auditing/webui/log_analysis/sslvpn_service/tabs/device/deviceList.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/extensions/auditing/webui/log_analysis/sslvpn_service/tabs/device/deviceList.controller.js	(working copy)
@@ -7,7 +7,8 @@
         '$filter',
         'timeService',
         'localStorageService',
-        function (userService, deviceService, $scope, $filter, timeService, localStorageService) {
+        'roleMgmtService',
+        function (userService, deviceService, $scope, $filter, timeService, localStorageService, roleMgmtService) {
 
             $('#start').datetimepicker({
                 autoclose: true,
@@ -19,7 +20,8 @@
             });
             var deviceListViewModel = this;
             deviceListViewModel.showHelpContent = false;
-
+            $scope.role_info = localStorageService.getWebStorage('role_info');
+            $scope.isDevicesLoaded = false;
             $scope.currentPageIndex = 1;
             $scope.pageSize = 15;
             $scope.onPageChange = function (newPage) {
@@ -69,7 +71,9 @@
 
                 deviceListViewModel.startTime = start.format('yyyy-mm-dd HH:MM:ss');
                 deviceListViewModel.endTime = now.format('yyyy-mm-dd HH:MM:ss');
-                deviceListViewModel.reload();
+                if ($scope.isDevicesLoaded) {
+                    deviceListViewModel.reload();
+                }
             }
 
             deviceListViewModel.applyTimeRange = function () {
@@ -87,43 +91,63 @@
             }
 
             deviceListViewModel.refresh = function () {
-                if (deviceListViewModel.currentRange != 'custom') {
+                if (deviceListViewModel.currentRange !== 'custom') {
                     deviceListViewModel.changeTimeGap(deviceListViewModel.currentRange)
                 } else {
-                    deviceListViewModel.reload()
+                    deviceListViewModel.reload();
                 }
             }
 
             var device_load = false;
             var log_load = false;
-            deviceService.getDeviceList().then(function (res) {
+            deviceListViewModel.remoteIPs = [];
+            roleMgmtService.getRoleDeviceGroupMapping($scope.role_info).then(function (res) {
+                deviceListViewModel.remoteIPs = [];
                 if (res && res.status === 200) {
-                    deviceListViewModel.deviceList = {};
-                    _.each(res.data, function (data) {
-                        deviceListViewModel.deviceList[data["ip"]] = data;
-                    })
-                    device_load = true;
-                    if (log_load) {
-                        _.each(deviceListViewModel.deviceInfoList_tmp, function (data) {
-                            if (deviceListViewModel.deviceList[data["host_name"]]) {
-                                data["device"] = {
-                                    "name": deviceListViewModel.deviceList[data["host_name"]].name,
-                                    "type": deviceListViewModel.deviceList[data["host_name"]].type,
-                                    "id": deviceListViewModel.deviceList[data["host_name"]].id,
-                                    "ip": deviceListViewModel.deviceList[data["host_name"]].ip,
-                                    "device_group": deviceListViewModel.deviceList[data["host_name"]].device_group,
-                                };
-                            } else {
-                                data["device"] = {
-                                    "name": '-',
-                                    "type": '-',
-                                    "id": '-',
-                                    "ip": '-',
-                                    "device_group": '-',
-                                };
+                    try {
+                        let data = res.data;
+                        if (data.length > 1) {
+                            let deviceGMap = data[1]['result'];
+                            let device_list = [];
+                            deviceGMap.forEach(function (deviceGroup) {
+                                deviceGroup['device_list'].forEach(function (device) {
+                                    device_list.push(device);
+                                    deviceListViewModel.remoteIPs.push(device.ip);
+                                })
+                            })
+                            deviceListViewModel.deviceList = {};
+                            _.each(device_list, function (data) {
+                                deviceListViewModel.deviceList[data["ip"]] = data;
+                            })
+                            device_load = true;
+                            if (log_load) {
+                                _.each(deviceListViewModel.deviceInfoList_tmp, function (data) {
+                                    if (deviceListViewModel.deviceList[data["host_name"]]) {
+                                        data["device"] = {
+                                            "name": deviceListViewModel.deviceList[data["host_name"]].name,
+                                            "type": deviceListViewModel.deviceList[data["host_name"]].type,
+                                            "id": deviceListViewModel.deviceList[data["host_name"]].id,
+                                            "ip": deviceListViewModel.deviceList[data["host_name"]].ip,
+                                            "device_group": deviceListViewModel.deviceList[data["host_name"]].device_group,
+                                        };
+                                    } else {
+                                        data["device"] = {
+                                            "name": '-',
+                                            "type": '-',
+                                            "id": '-',
+                                            "ip": '-',
+                                            "device_group": '-',
+                                        };
+                                    }
+                                })
+                                deviceListViewModel.deviceInfoList = deviceListViewModel.deviceInfoList_tmp;
                             }
-                        })
-                        deviceListViewModel.deviceInfoList = deviceListViewModel.deviceInfoList_tmp;
+                            $scope.isDevicesLoaded = true;
+                            deviceListViewModel.reload();
+                        }
+                    } catch (error) {
+                        console.log('500 - Internal server error.');
+                        alert('500 - Internal server error. Failed to fetch device group mapping info.');
                     }
                 }
             });
@@ -140,7 +164,7 @@
                 var startstamp = new Date(deviceListViewModel.startTime.replace(/-/g, "/")).getTime();
                 var endstamp = new Date(deviceListViewModel.endTime.replace(/-/g, "/")).getTime();
 
-                userService.getDeviceList(startstamp, endstamp).then(function (res) {
+                userService.getDeviceList(startstamp, endstamp, deviceListViewModel.remoteIPs).then(function (res) {
                     deviceListViewModel.loading = false;
                     if (res && res.status === 200) {
                         log_load = true;
@@ -175,12 +199,14 @@
             if (localStorageService.getWebStorage('timeRange')) {
                 var timeRange = localStorageService.getWebStorage('timeRange');
                 deviceListViewModel.currentRange = timeRange.currentRange;
-                if (timeRange.currentRange != 'custom') {
+                if (timeRange.currentRange !== 'custom') {
                     deviceListViewModel.changeTimeGap(timeRange.currentRange);
                 } else {
                     deviceListViewModel.startTime = timeRange.startTime;
                     deviceListViewModel.endTime = timeRange.endTime;
-                    deviceListViewModel.reload()
+                    if ($scope.isDevicesLoaded) {
+                        deviceListViewModel.reload();
+                    }
                 }
             } else {
                 deviceListViewModel.changeTimeGap('1d');
Index: /branches/amp_3_6_0_role/extensions/auditing/webui/log_analysis/sslvpn_service/tabs/statistics/server.controller.js
===================================================================
--- /branches/amp_3_6_0_role/extensions/auditing/webui/log_analysis/sslvpn_service/tabs/statistics/server.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/extensions/auditing/webui/log_analysis/sslvpn_service/tabs/statistics/server.controller.js	(working copy)
@@ -10,9 +10,10 @@
         'timeService',
         'localStorageService',
         'userService',
-        function ($scope, $rootScope, $state, $stateParams, $uibModal, $filter, $location, timeService, localStorageService, userService) {
+        'roleMgmtService',
+        function ($scope, $rootScope, $state, $stateParams, $uibModal, $filter, $location, timeService, localStorageService, userService, roleMgmtService) {
             var serverStatisticsViewModal = this;
-
+            $scope.role_info = localStorageService.getWebStorage('role_info');
             $scope.currentPageIndex = 1;
             $scope.pageSize = 15;
             $scope.onPageChange = function (newPage) {
@@ -95,6 +96,28 @@
 
             //     getSeverUsageStatisticList(pre_month_time, current_time);
             // }
+            serverStatisticsViewModal.remoteIPs = [];
+
+            roleMgmtService.getRoleDeviceGroupMapping($scope.role_info).then(function (res) {
+                serverStatisticsViewModal.remoteIPs = [];
+                if (res && res.status === 200) {
+                    try {
+                        let data = res.data;
+                        if (data.length > 1) {
+                            let deviceGMap = data[1]['result'];
+                            deviceGMap.forEach(function (deviceGroup) {
+                                deviceGroup['device_list'].forEach(function (device) {
+                                    serverStatisticsViewModal.remoteIPs.push(device.ip);
+                                })
+                            })
+                            getSeverUsageStatisticList(serverStatisticsViewModal.startTime, serverStatisticsViewModal.endTime);
+                        }
+                    } catch (err) {
+                        console.log('500 - Internal server error.');
+                        alert('500 - Internal server error. Failed to fetch device group mapping info.');
+                    }
+                }
+            });
 
             function getSeverUsageStatisticList(start_time, end_time) {
                 $scope.currentPageIndex = 1;
@@ -111,7 +134,7 @@
                     top_type: serverStatisticsViewModal.type
                 };
 
-                userService.getUserTopRanking(data).then(function (resp) {
+                userService.getUserTopRanking(data, serverStatisticsViewModal.remoteIPs).then(function (resp) {
                     serverStatisticsViewModal.isSearching = false;
                     serverStatisticsViewModal.isLoading = false;
 
@@ -143,7 +166,7 @@
                 serverStatisticsViewModal.startTime = start.format('yyyy-mm-dd HH:MM:ss');
                 serverStatisticsViewModal.endTime = now.format('yyyy-mm-dd HH:MM:ss');
             }
-            getSeverUsageStatisticList(serverStatisticsViewModal.startTime, serverStatisticsViewModal.endTime);
+            // getSeverUsageStatisticList(serverStatisticsViewModal.startTime, serverStatisticsViewModal.endTime);
 
             serverStatisticsViewModal.exportData = function () {
                 var exportStatisticLog = confirm($filter("T")("Are you sure to export Statistics Logs?"));
Index: /branches/amp_3_6_0_role/extensions/auditing/webui/log_analysis/sslvpn_service/tabs/statistics/user.controller.js
===================================================================
--- /branches/amp_3_6_0_role/extensions/auditing/webui/log_analysis/sslvpn_service/tabs/statistics/user.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/extensions/auditing/webui/log_analysis/sslvpn_service/tabs/statistics/user.controller.js	(working copy)
@@ -11,7 +11,8 @@
         'localStorageService',
         'userService',
         'deviceService',
-        function ($scope, $rootScope, $state, $stateParams, $uibModal, $filter, $location, timeService, localStorageService, userService, deviceService) {
+        'roleMgmtService',
+        function ($scope, $rootScope, $state, $stateParams, $uibModal, $filter, $location, timeService, localStorageService, userService, deviceService, roleMgmtService) {
             var userLogsStatisticsModal = this;
 
             $scope.currentPageIndex = 1;
@@ -26,37 +27,56 @@
                 getUserTopRankingInfo(userLogsStatisticsModal.startTime, userLogsStatisticsModal.endTime);
             });
             userLogsStatisticsModal.showHelpContent = false;
-
+            $scope.role_info = localStorageService.getWebStorage('role_info');
             var device_load = false;
             var log_load = false;
-            deviceService.getDeviceList().then(function (res) {
+            userLogsStatisticsModal.remoteIPs = [];
+            roleMgmtService.getRoleDeviceGroupMapping($scope.role_info).then(function (res) {
+                userLogsStatisticsModal.remoteIPs = [];
                 if (res && res.status === 200) {
-                    userLogsStatisticsModal.deviceList = {};
-                    _.each(res.data, function (data) {
-                        userLogsStatisticsModal.deviceList[data["ip"]] = data;
-                    })
-                    device_load = true;
-                    if (log_load) {
-                        _.each(userLogsStatisticsModal.rankingDataList_tmp, function (data) {
-                            if (userLogsStatisticsModal.deviceList[data["host_name"]]) {
-                                data["device"] = {
-                                    "name": userLogsStatisticsModal.deviceList[data["host_name"]].name,
-                                    "type": userLogsStatisticsModal.deviceList[data["host_name"]].type,
-                                    "id": userLogsStatisticsModal.deviceList[data["host_name"]].id,
-                                    "ip": userLogsStatisticsModal.deviceList[data["host_name"]].ip,
-                                    "device_group": userLogsStatisticsModal.deviceList[data["host_name"]].device_group,
-                                };
-                            } else {
-                                data["device"] = {
-                                    "name": '-',
-                                    "type": '-',
-                                    "id": '-',
-                                    "ip": '-',
-                                    "device_group": '-',
-                                };
+                    try {
+                        let data = res.data;
+                        if (data.length > 1) {
+                            let deviceGMap = data[1]['result'];
+                            let device_list = [];
+                            deviceGMap.forEach(function (deviceGroup) {
+                                deviceGroup['device_list'].forEach(function (device) {
+                                    device_list.push(device);
+                                    userLogsStatisticsModal.remoteIPs.push(device.ip);
+                                })
+                            })
+                            userLogsStatisticsModal.deviceList = {};
+                            _.each(device_list, function (data) {
+                                userLogsStatisticsModal.deviceList[data["ip"]] = data;
+                            })
+                            device_load = true;
+                            if (log_load) {
+                                _.each(userLogsStatisticsModal.rankingDataList_tmp, function (data) {
+                                    if (userLogsStatisticsModal.deviceList[data["host_name"]]) {
+                                        data["device"] = {
+                                            "name": userLogsStatisticsModal.deviceList[data["host_name"]].name,
+                                            "type": userLogsStatisticsModal.deviceList[data["host_name"]].type,
+                                            "id": userLogsStatisticsModal.deviceList[data["host_name"]].id,
+                                            "ip": userLogsStatisticsModal.deviceList[data["host_name"]].ip,
+                                            "device_group": userLogsStatisticsModal.deviceList[data["host_name"]].device_group,
+                                        };
+                                    } else {
+                                        data["device"] = {
+                                            "name": '-',
+                                            "type": '-',
+                                            "id": '-',
+                                            "ip": '-',
+                                            "device_group": '-',
+                                        };
+                                    }
+                                })
+                                userLogsStatisticsModal.rankingDataList = userLogsStatisticsModal.rankingDataList_tmp;
                             }
-                        })
-                        userLogsStatisticsModal.rankingDataList = userLogsStatisticsModal.rankingDataList_tmp;
+                            getUserTopRankingInfo(userLogsStatisticsModal.startTime, userLogsStatisticsModal.endTime);
+                        }
+                    } catch (err) {
+                        console.log('500 - Internal server error.');
+                        alert('500 - Internal server error. Failed to fetch device group mapping info.');
                     }
                 }
             });
@@ -147,7 +167,7 @@
                 };
 
                 log_load = false;
-                userService.getUserTopRanking(data).then(function (res) {
+                userService.getUserTopRanking(data, userLogsStatisticsModal.remoteIPs).then(function (res) {
                     userLogsStatisticsModal.isSearching = false;
                     userLogsStatisticsModal.isLoading = false;
                     if (res && res.status === 200) {
@@ -251,10 +271,10 @@
                 var now = new Date();
                 var start = new Date();
                 start.setTime(now.getTime() - timeService.parseDuration('1d'));
-                logStatisticsViewModel.startTime = start.format('yyyy-mm-dd HH:MM:ss');
-                logStatisticsViewModel.endTime = now.format('yyyy-mm-dd HH:MM:ss');
+                userLogsStatisticsModal.startTime = start.format('yyyy-mm-dd HH:MM:ss');
+                userLogsStatisticsModal.endTime = now.format('yyyy-mm-dd HH:MM:ss');
             }
-            getUserTopRankingInfo(userLogsStatisticsModal.startTime, userLogsStatisticsModal.endTime);
+            // getUserTopRankingInfo(userLogsStatisticsModal.startTime, userLogsStatisticsModal.endTime);
 
             userLogsStatisticsModal.exportData = function () {
                 var exportStatisticLog = confirm($filter("T")("Are you sure to export Statistics Logs?"));
Index: /branches/amp_3_6_0_role/extensions/auditing/webui/log_analysis/sslvpn_service/tabs/user/userList.controller.js
===================================================================
--- /branches/amp_3_6_0_role/extensions/auditing/webui/log_analysis/sslvpn_service/tabs/user/userList.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/extensions/auditing/webui/log_analysis/sslvpn_service/tabs/user/userList.controller.js	(working copy)
@@ -10,7 +10,8 @@
         'deviceService',
         'timeService',
         'localStorageService',
-        function ($scope, $rootScope, $state, $uibModal, $filter, userService, deviceService, timeService, localStorageService) {
+        'roleMgmtService',
+        function ($scope, $rootScope, $state, $uibModal, $filter, userService, deviceService, timeService, localStorageService, roleMgmtService) {
 
             $('#start').datetimepicker({
                 autoclose: true,
@@ -21,7 +22,7 @@
                 endDate: new Date()
             });
             var userListViewModel = this;
-
+            $scope.role_info = localStorageService.getWebStorage('role_info');
             userListViewModel.showHelpContent = false;
 
             $scope.currentPageIndex = 1;
@@ -106,75 +107,60 @@
                     'startTime': userListViewModel.startTime,
                     'endTime': userListViewModel.endTime
                 });
-
-                // var device_load = false;
-                // var log_load = false;
-
-                deviceService.getDeviceList().then(function (res) {
+                let remoteIPs = [];
+                roleMgmtService.getRoleDeviceGroupMapping($scope.role_info).then(function (res) {
                     if (res && res.status === 200) {
-                        var deviceMap = {};
-                        _.each(res.data, function (data) {
-                            deviceMap[data["ip"]] = data;
-                        })
-
-                        var startstamp = new Date(userListViewModel.startTime.replace(/-/g, "/")).getTime();
-                        var endstamp = new Date(userListViewModel.endTime.replace(/-/g, "/")).getTime();
-
-                        userService.getUserList(startstamp, endstamp).then(function (resp) {
-                            userListViewModel.loading = false;
-                            if (resp && resp.status === 200) {
-                                _.each(resp.data, function (data) {
-                                    if (deviceMap[data["host_name"]]) {
-                                        data["device"] = {
-                                            "name": deviceMap[data["host_name"]].name,
-                                            "type": deviceMap[data["host_name"]].type,
-                                            "id": deviceMap[data["host_name"]].id,
-                                            "ip": deviceMap[data["host_name"]].ip,
-                                            "device_group": deviceMap[data["host_name"]].device_group,
-                                        };
-                                    } else {
-                                        data["device"] = {
-                                            "name": '-',
-                                            "type": '-',
-                                            "id": '-',
-                                            "ip": '-',
-                                            "device_group": '-',
-                                        };
+                        try {
+                            let data = res.data;
+                            if (data.length > 1) {
+                                let deviceGMap = data[1]['result'];
+                                let device_list = [];
+                                deviceGMap.forEach(function (deviceGroup) {
+                                    deviceGroup['device_list'].forEach(function (device) {
+                                        device_list.push(device);
+                                        remoteIPs.push( device.ip);
+                                    })
+                                })
+                                var deviceMap = {};
+                                _.each(device_list, function (data) {
+                                    deviceMap[data["ip"]] = data;
+                                })
+
+                                var startstamp = new Date(userListViewModel.startTime.replace(/-/g, "/")).getTime();
+                                var endstamp = new Date(userListViewModel.endTime.replace(/-/g, "/")).getTime();
+
+                                userService.getUserList(startstamp, endstamp, remoteIPs).then(function (resp) {
+                                    userListViewModel.loading = false;
+                                    if (resp && resp.status === 200) {
+                                        _.each(resp.data, function (data) {
+                                            if (deviceMap[data["host_name"]]) {
+                                                data["device"] = {
+                                                    "name": deviceMap[data["host_name"]].name,
+                                                    "type": deviceMap[data["host_name"]].type,
+                                                    "id": deviceMap[data["host_name"]].id,
+                                                    "ip": deviceMap[data["host_name"]].ip,
+                                                    "device_group": deviceMap[data["host_name"]].device_group,
+                                                };
+                                            } else {
+                                                data["device"] = {
+                                                    "name": '-',
+                                                    "type": '-',
+                                                    "id": '-',
+                                                    "ip": '-',
+                                                    "device_group": '-',
+                                                };
+                                            }
+                                        });
+                                        userListViewModel.userInfoList = resp.data;
                                     }
                                 });
-                                userListViewModel.userInfoList = resp.data;
                             }
-                        });
-
-
-                        // device_load = true;
-                        // if (log_load) {
-                        //     _.each(userListViewModel.userInfoList_tmp, function (data) {
-                        //         data["device"] = deviceMap[data["host_name"]];
-                        //     })
-                        //     userListViewModel.userInfoList = userListViewModel.userInfoList_tmp;
-                        //     userListViewModel.loading = false;
-                        // }
-                    }
+                            } catch (error) {
+                                console.log('500 - Internal server error.');
+                                alert('500 - Internal server error. Failed to fetch device group mapping info.');
+                            }
+                        }
                 });
-                // function get_userListInfo() {
-                //     userService.getUserList().then(function (res) {
-                //         if (res && res.status === 200) {
-                //             log_load = true;
-                //             if (device_load) {
-                //                 _.each(res.data, function (data) {
-                //                     data["device"] = deviceMap[data["host_name"]];
-                //                 });
-                //                 userListViewModel.userInfoList = res.data;
-                //             } else {
-                //                 userListViewModel.userInfoList_tmp = res.data;
-                //                 userListViewModel.loading = false;
-                //             }
-                //         }
-                //     });
-                // }
-
-                // get_userListInfo();
             }
             var timeRange = localStorageService.getWebStorage('timeRange');
             if (timeRange) {
@@ -277,16 +263,6 @@
                                 continue;
                             }
                         }
-                        // if (userListViewModel.last_login_time_before) {
-                        //     if (userListViewModel.userInfoList[i].last_login_timestamp < new Date(userListViewModel.last_login_time_before).valueOf()) {
-                        //         continue;
-                        //     }
-                        // }
-                        // if (userListViewModel.last_login_time_after) {
-                        //     if (userListViewModel.userInfoList[i].last_login_timestamp > new Date(userListViewModel.last_login_time_after).valueOf()) {
-                        //         continue;
-                        //     }
-                        // }
                         str += userListViewModel.userInfoList[i].user_name + '\t,' +
                             userListViewModel.userInfoList[i].device.name + '\t,' +
                             userListViewModel.userInfoList[i].device.device_group + '\t,' +
@@ -304,74 +280,8 @@
             };
         }
     ])
-    // .directive('stDateRange', ['$timeout', function ($timeout) {
-    //     return {
-    //         restrict: 'E',
-    //         require: '^stTable',
-    //         scope: {
-    //             before: '=',
-    //             after: '='
-    //         },
-    //         template: '<form class="form-inline" role="form">' +
-    //             '<input type="text" class="form-control" placeholder="{{\'Start Time\' | T}}" ' +
-    //             'ng-model="before" data-date-format="yyyy-mm-dd hh:ii"/ readonly="readonly">' +
-    //             '<span>&minus;</span>' +
-    //             '<input type="text" class="form-control" placeholder="{{\'End Time\' | T}}" ' +
-    //             'ng-model="after" data-date-format="yyyy-mm-dd hh:ii"/ readonly="readonly">' +
-    //             '</form>',
-
-    //         link: function (scope, element, attr, table) {
-
-    //             var inputs = element.find('input');
-    //             var inputBefore = angular.element(inputs[0]);
-    //             var inputAfter = angular.element(inputs[1]);
-    //             var predicateName = attr.predicate;
-
-    //             inputBefore.datetimepicker({
-    //                 autoclose: true,
-    //                 clearBtn: true,
-    //                 endDate: new Date()
-    //             })
-    //                 .on('changeDate', function (ev) {
-    //                     var query = {};
-    //                     if (!scope.isBeforeOpen && !scope.isAfterOpen) {
-    //                         if (scope.before) {
-    //                             query.before = scope.before;
-    //                         }
-    //                         if (scope.after) {
-    //                             query.after = scope.after;
-    //                         }
-    //                         scope.$apply(function () {
-    //                             table.search(query, predicateName);
-    //                         })
-    //                     }
-    //                 });
-    //             inputAfter.datetimepicker({
-    //                 pickerPosition: "bottom-left",
-    //                 autoclose: true,
-    //                 clearBtn: true,
-    //                 endDate: new Date()
-    //             })
-    //                 .on('changeDate', function (ev) {
-    //                     var query = {};
-    //                     if (!scope.isBeforeOpen && !scope.isAfterOpen) {
-    //                         if (scope.before) {
-    //                             query.before = scope.before;
-    //                         }
-    //                         if (scope.after) {
-    //                             query.after = scope.after;
-    //                         }
-    //                         scope.$apply(function () {
-    //                             table.search(query, predicateName);
-    //                         })
-    //                     }
-    //                 });
-    //         }
-    //     }
-    // }])
     .filter('myFilter', function () {
         return function (array, expression) {
-            //console.log(expression);
             return array.filter(function (val, index) {
                 if (expression.user_name) {
                     if (val.user_name.indexOf(expression.user_name) == -1) {
@@ -401,19 +311,6 @@
                         return false;
                     }
                 }
-                // if (expression.last_login_time) {
-                //     if (expression.last_login_time.before) {
-                //         if (val.last_login_timestamp < new Date(expression.last_login_time.before).valueOf()) {
-                //             return false;
-                //         }
-                //     }
-                //     if (expression.last_login_time.after) {
-                //         if (val.last_login_timestamp > new Date(expression.last_login_time.after).valueOf()) {
-                //             return false;
-                //         }
-                //     }
-
-                // }
                 return true;
             });
         }
Index: /branches/amp_3_6_0_role/extensions/monitoring/webui/event/query_event/query_event.controller.js
===================================================================
--- /branches/amp_3_6_0_role/extensions/monitoring/webui/event/query_event/query_event.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/extensions/monitoring/webui/event/query_event/query_event.controller.js	(working copy)
@@ -391,12 +391,14 @@
         'dashboardService',
         'monitoringService',
         'modalData',
-        function ($scope, $rootScope, $state, $stateParams, $uibModal, $uibModalInstance, $filter, dashboardService, monitoringService, modalData) {
+        'localStorageService',
+        function ($scope, $rootScope, $state, $stateParams, $uibModal, $uibModalInstance, $filter, dashboardService, monitoringService, modalData, localStorageService) {
             var queryViewModel = this;
             queryViewModel.modalClose = function () {
                 $uibModalInstance.dismiss();
             };
-
+            $scope.role_info = localStorageService.getWebStorage('role_info');
+            $scope.isDeviceAdmin = $scope.role_info.role_id !== null && $scope.role_info.role_id !== '0';
             $scope.currentPageIndex = 1;
             $scope.pageSize = 10;
             $scope.onPageChange = function (newPage) {
@@ -432,11 +434,22 @@
             }
 
             monitoringService.getDeviceList().then(function (resp) {
-                var deviceMap = {}
+                let deviceMap = {}
+                let agentHost = '';
                 _.each(resp, function (host) {
                     deviceMap[host.ip] = host;
+                    if (agentHost === '') {
+                        agentHost = agentHost + '/' + host.ip;
+                    } else {
+                        agentHost = agentHost + '|' + host.ip;
+                    }
                 })
-                var query = 'SELECT time, agent_host, server_id, quantity FROM event_detection ' + timeCondition + otherCondition + ' GROUP BY event_name, product order by time desc;'
+                if (agentHost !== '') agentHost += '/';
+                let query = 'SELECT time, agent_host, server_id, quantity FROM event_detection ' + timeCondition + otherCondition + ' GROUP BY event_name, product order by time desc;'
+                if ($scope.isDeviceAdmin) {
+                    query = 'SELECT time, agent_host, server_id, quantity FROM event_detection ' + timeCondition + otherCondition + ' and agent_host =~ '+ agentHost +' GROUP BY event_name, product order by time desc;'
+                }
+                if (($scope.isDeviceAdmin && agentHost !== '') || !$scope.isDeviceAdmin) {
                 dashboardService.influxdb_proxy({ "q": query }).then(function (res) {
                     queryViewModel.loading = false;
                     if (res && res.status == 200) {
@@ -480,6 +493,7 @@
                         queryViewModel.eventList = eventList
                     }
                 });
+                }
             })
         }
     ])
Index: /branches/amp_3_6_0_role/extensions/monitoring/webui/monitoring.service.js
===================================================================
--- /branches/amp_3_6_0_role/extensions/monitoring/webui/monitoring.service.js	(revision 2350)
+++ /branches/amp_3_6_0_role/extensions/monitoring/webui/monitoring.service.js	(working copy)
@@ -8,7 +8,8 @@
         'dashboardService',
         'localStorageService',
         'deviceService',
-        function ($rootScope, $q, $filter, $http, api, dashboardService, localStorageService, deviceService) {
+        'roleMgmtService',
+        function ($rootScope, $q, $filter, $http, api, dashboardService, localStorageService, deviceService, roleMgmtService) {
             return {
                 getDeviceList: getDeviceList,
                 getVirtualService: getVirtualService,
@@ -17,31 +18,43 @@
             };
 
             function getDeviceList() {
-                var deferred = $q.defer();
-                deviceService.getDeviceList().then(function (res) {
-                    var deviceList = [];
-                    var device_type_info = localStorageService.getWebStorage("device_type_info");
-                    if (res && res.status === 200 && res.data instanceof Array) {
-                        _.each(res.data, function (host) {
-                            if (device_type_info.ADC_TYPE_LIST.indexOf(host.type.toLowerCase()) != -1) {
-                                host.general_type = "adc"
-                            } else if (device_type_info.VPN_TYPE_LIST.indexOf(host.type.toLowerCase()) != -1) {
-                                host.general_type = "vpn"
+                let deferred = $q.defer();
+                let role_info = localStorageService.getWebStorage('role_info');
+                let device_list = [];
+                let device_type_info = localStorageService.getWebStorage("device_type_info");
+                roleMgmtService.getRoleDeviceGroupMapping(role_info).then(function (res) {
+                    if (res && res.status === 200) {
+                        try {
+                            let data = res.data;
+                            if (data.length > 1) {
+                                let deviceMap = data[1]['result'];
+                                deviceMap.forEach(function (deviceGroup) {
+                                    deviceGroup['device_list'].forEach(function (device) {
+                                        if (device_type_info.ADC_TYPE_LIST.indexOf(device.type.toLowerCase()) !== -1) {
+                                            device.general_type = "adc"
+                                        } else if (device_type_info.VPN_TYPE_LIST.indexOf(host.type.toLowerCase()) !== -1) {
+                                            device.general_type = "vpn"
+                                        }
+                                        device_list.push(device);
+                                    })
+                                })
                             }
-                            deviceList.push(host)
-                        });
+                            deferred.resolve(device_list);
+                        } catch (e) {
+                            console.log('500 - Internal server error.');
+                            alert('500 - Internal server error. Failed to fetch device group mapping info.');
+                        }
                     }
-                    deferred.resolve(deviceList);
-                });
+                })
                 return deferred.promise;
             }
 
             function getVirtualService(device_ip) {
                 var deferred = $q.defer();
                 var query = "select count(URLHits) from virtualStats where time > now()-20s and agent_host='" + device_ip + "' group by ServerId;"
-                dashboardService.influxdb_proxy({ "q": query }).then(function (res) {
+                dashboardService.influxdb_proxy({"q": query}).then(function (res) {
                     var serverList = []
-                    if (res && res.status == 200) {
+                    if (res && res.status === 200) {
                         _.each(res.data.results[0].series, function (series) {
                             serverList.push({
                                 "name": series.tags.ServerId,
@@ -53,14 +66,14 @@
                     deferred.resolve(serverList);
                 });
                 return deferred.promise;
-            };
+            }
 
             function getRealService(device_ip) {
                 var deferred = $q.defer();
                 var query = "select count(rsTotalHits) from realStats where time > now()-20s and agent_host='" + device_ip + "' group by realServerId;"
-                dashboardService.influxdb_proxy({ "q": query }).then(function (res) {
+                dashboardService.influxdb_proxy({"q": query}).then(function (res) {
                     var serverList = []
-                    if (res && res.status == 200) {
+                    if (res && res.status === 200) {
                         _.each(res.data.results[0].series, function (series) {
                             serverList.push({
                                 "name": series.tags.realServerId,
@@ -72,14 +85,14 @@
                     deferred.resolve(serverList);
                 });
                 return deferred.promise;
-            };
+            }
 
             function getVirtualSite(device_ip) {
                 var deferred = $q.defer();
                 var query = "select count(ActiveSessions) from virtualSiteStats where time > now()-20s and agent_host='" + device_ip + "' group by Id;"
-                dashboardService.influxdb_proxy({ "q": query }).then(function (res) {
+                dashboardService.influxdb_proxy({"q": query}).then(function (res) {
                     var serverList = []
-                    if (res && res.status == 200) {
+                    if (res && res.status === 200) {
                         _.each(res.data.results[0].series, function (series) {
                             serverList.push({
                                 "name": series.tags.Id,
@@ -91,6 +104,6 @@
                     deferred.resolve(serverList);
                 });
                 return deferred.promise;
-            };
+            }
         }
     ]);
\ No newline at end of file
Index: /branches/amp_3_6_0_role/extensions/monitoring/webui/resource/device/device.controller.js
===================================================================
--- /branches/amp_3_6_0_role/extensions/monitoring/webui/resource/device/device.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/extensions/monitoring/webui/resource/device/device.controller.js	(working copy)
@@ -12,9 +12,10 @@
         'dashboardService',
         'storageService',
         'localStorageService',
-        function ($scope, $rootScope, $state, $stateParams, $location, $uibModal, $filter, cmService, deviceService, dashboardService, storageService, localStorageService) {
+        'roleMgmtService',
+        function ($scope, $rootScope, $state, $stateParams, $location, $uibModal, $filter, cmService, deviceService, dashboardService, storageService, localStorageService, roleMgmtService) {
             $rootScope.title = 'Devices';
-
+            $scope.role_info = localStorageService.getWebStorage('role_info');
             var modalViewModel = this;
 
             $scope.currentPageIndex = 1;
@@ -116,13 +117,19 @@
 
             modalViewModel.gridColSpan = 6;
             modalViewModel.deviceList = [];
-            var getDeviceMonitoringData = function () {
-                var post_data = {
+            let getDeviceMonitoringData = function (isDeviceAdmin, agentHost) {
+                let select_query = "SELECT last(cpu_usage) as cpu, last(mem_usage) as mem, last(net_mem_usage) as net_mem, last(connections) as connections FROM snmp_system WHERE $timeFilter GROUP BY agent_host; " +
+                    "SELECT non_negative_derivative(first(total_in), 1s)*8 as received, non_negative_derivative(first(total_out), 1s)*8 as sent FROM snmp_system WHERE $timeFilter GROUP BY time($interval), agent_host";
+                if(isDeviceAdmin) {
+                    select_query = "SELECT last(cpu_usage) as cpu, last(mem_usage) as mem, last(net_mem_usage) as net_mem, last(connections) as connections FROM snmp_system WHERE agent_host =~ "+ agentHost +" and $timeFilter GROUP BY agent_host; " +
+                        "SELECT non_negative_derivative(first(total_in), 1s)*8 as received, non_negative_derivative(first(total_out), 1s)*8 as sent FROM snmp_system WHERE agent_host =~ "+ agentHost +" and $timeFilter GROUP BY time($interval), agent_host";
+                }
+                let post_data = {
                     "from": "now-30s",
                     "to": "now",
                     "queries": [{
                         "datasourceId": 1,
-                        "query": "SELECT last(cpu_usage) as cpu, last(mem_usage) as mem, last(net_mem_usage) as net_mem, last(connections) as connections FROM snmp_system WHERE $timeFilter GROUP BY agent_host; SELECT non_negative_derivative(first(total_in), 1s)*8 as received, non_negative_derivative(first(total_out), 1s)*8 as sent FROM snmp_system WHERE $timeFilter GROUP BY time($interval), agent_host",
+                        "query": select_query,
                         "rawQuery": true,
                         "resultFormat": "time_series"
                     }]
@@ -130,7 +137,7 @@
                 dashboardService
                     .get_composer_data('/composer/tsdb/query', JSON.stringify(post_data))
                     .then(function (res) {
-                        if (res && res.data.code == 0) {
+                        if (res && res.data.code === 0) {
                             var deviceMap = {};
                             _.each(res.data.data.results['A'].series, function (series) {
                                 if (deviceMap[series.tags['agent_host']]) {
@@ -181,23 +188,51 @@
 
             modalViewModel.refresh = function () {
                 modalViewModel.loading = true;
-                deviceService.getDeviceList().then(function (res) {
+                let agentHost = '';
+                let isDeviceAdmin = $scope.role_info.role_id !== null && $scope.role_info.role_id !== '0';
+                roleMgmtService.getRoleDeviceGroupMapping($scope.role_info).then(function (res) {
                     modalViewModel.loading = false;
                     if (res && res.status === 200) {
-                        //get graph data for Network/CPU/Memory/Session Number
-                        var deviceList = [];
-                        _.each(res.data, function (each_data) {
-                            each_data.graph_data = {
-                                'received': 'N/A',
-                                'sent': 'N/A',
-                                'cpu_usage': 'N/A',
-                                'mem_usage': 'N/A',
-                                'net_mem_usage': 'N/A',
-                            };
-                            deviceList.push(each_data);
-                        });
-                        modalViewModel.deviceList = deviceList;
-                        getDeviceMonitoringData()
+                        try {
+                            let data = res.data;
+                            if (data.length > 1) {
+                                try {
+                                    let deviceMap = data[1]['result'];
+                                    deviceMap.forEach(function (deviceGroup) {
+                                        deviceGroup['name'] = deviceGroup['group_name'];
+                                        deviceGroup['device_list'].forEach(function (device) {
+                                            device.graph_data = {
+                                                'received': 'N/A',
+                                                'sent': 'N/A',
+                                                'cpu_usage': 'N/A',
+                                                'mem_usage': 'N/A',
+                                                'net_mem_usage': 'N/A',
+                                            };
+                                            if (agentHost === '') {
+                                                agentHost = agentHost + '/' + device.ip;
+                                            } else {
+                                                agentHost = agentHost + '|' + device.ip;
+                                            }
+                                            modalViewModel.deviceList.push(device);
+                                        })
+                                    })
+                                    modalViewModel.deviceGroupList = deviceMap;
+                                    if (agentHost !== '') agentHost += '/';
+                                    if ((isDeviceAdmin && agentHost !== '') || !isDeviceAdmin) {
+                                    getDeviceMonitoringData(isDeviceAdmin, agentHost );
+                                    }
+                                } catch (e) {
+                                    console.error('Error getRoleDeviceGroupMapping returned error.' + e);
+                                    modalViewModel.deviceList = []
+                                    modalViewModel.deviceGroupList = [];
+                                }
+                            }
+                            if (modalViewModel.deviceGroupList.length > 0) modalViewModel.showDeviceGroup = true;
+                            if (modalViewModel.deviceList.length > 0)modalViewModel.showDevice = true;
+                        } catch (e) {
+                            console.log('500 - Internal server error.');
+                            alert('500 - Internal server error. Failed to fetch device group mapping info.');
+                        }
                     }
                 });
             }
Index: /branches/amp_3_6_0_role/extensions/monitoring/webui/resource/resource.service.js
===================================================================
--- /branches/amp_3_6_0_role/extensions/monitoring/webui/resource/resource.service.js	(revision 2350)
+++ /branches/amp_3_6_0_role/extensions/monitoring/webui/resource/resource.service.js	(working copy)
@@ -2117,13 +2117,23 @@
                 return widgets
             };
 
-            function get_adc_ssl_cert() {
-                return apiService.get('/cm/get_adc_ssl_cert');
-            };
+            function get_adc_ssl_cert(roleId) {
+                let postData = {
+                    "data": JSON.stringify({
+                        "role_id": roleId,
+                    })
+                };
+                return apiService.post('/cm/get_adc_ssl_cert', postData);
+            }
 
-            function get_vpn_ssl_cert() {
-                return apiService.get('/cm/get_vpn_ssl_cert');
-            };
+            function get_vpn_ssl_cert(roleId) {
+                let postData = {
+                    "data": JSON.stringify({
+                        "role_id": roleId,
+                    })
+                };
+                return apiService.post('/cm/get_vpn_ssl_cert', postData);
+            }
 
             function getServiceUrlConfig(service_name, device_ip) {
                 var url = '/api/cm/extension_monitor/MonitorADSVSURL/_perform?action=get';
Index: /branches/amp_3_6_0_role/extensions/monitoring/webui/resource/slb/real_service.controller.js
===================================================================
--- /branches/amp_3_6_0_role/extensions/monitoring/webui/resource/slb/real_service.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/extensions/monitoring/webui/resource/slb/real_service.controller.js	(working copy)
@@ -12,9 +12,10 @@
         'monitorResourceService',
         'storageService',
         'localStorageService',
-        function ($scope, $rootScope, $state, $stateParams, $location, $uibModal, $filter, dashboardService, monitoringService, monitorResourceService, storageService, localStorageService) {
+        'roleMgmtService',
+        function ($scope, $rootScope, $state, $stateParams, $location, $uibModal, $filter, dashboardService, monitoringService, monitorResourceService, storageService, localStorageService, roleMgmtService) {
             var serviceViewModel = this;
-
+            $scope.role_info = localStorageService.getWebStorage('role_info');
             $scope.currentPageIndex = 1;
             $scope.pageSize = 15;
             $scope.onPageChange = function (newPage) {
@@ -22,10 +23,10 @@
             };
 
             $scope.multiSelectData = [
-                { id: 1, label: $filter('T')("Outstanding Requests") },
-                { id: 2, label: $filter('T')("Connections Per Second") },
-                { id: 3, label: $filter('T')("Received") },
-                { id: 4, label: $filter('T')("Sent") },
+                {id: 1, label: $filter('T')("Outstanding Requests")},
+                {id: 2, label: $filter('T')("Connections Per Second")},
+                {id: 3, label: $filter('T')("Received")},
+                {id: 4, label: $filter('T')("Sent")},
             ];
 
             var columnVisible = localStorageService.getWebStorage("TABLE_CUSTOM_COLUMN_VISIBLE");
@@ -35,7 +36,7 @@
             if (columnVisible.rsMonitor) {
                 $scope.multiSelectModel = columnVisible.rsMonitor;
             } else {
-                $scope.multiSelectModel = [{ id: 3 }, { id: 4 }];
+                $scope.multiSelectModel = [{id: 3}, {id: 4}];
             }
             $scope.multiSelectSettings = {
                 showCheckAll: false,
@@ -94,11 +95,15 @@
 
             serviceViewModel.gridColSpan = 7;
             serviceViewModel.listType = "SLB_rs";
-            var get_adc_ssl_cert = function () {
+            let get_adc_ssl_cert = function () {
                 serviceViewModel.adc_ssl_cert_map = undefined;
-                var adc_ssl_cert_map = {};
-                monitorResourceService.get_adc_ssl_cert().then(function (res) {
-                    if (res && res.status == 200) {
+                let adc_ssl_cert_map = {};
+                let roleId = $scope.role_info.role_id;
+                if (roleId === null) {
+                    roleId = '0';
+                }
+                monitorResourceService.get_adc_ssl_cert(roleId).then(function (res) {
+                    if (res && res.status === 200) {
                         if (res.data.state) {
                             _.each(res.data.data, function (cert) {
                                 adc_ssl_cert_map[cert.service_name] = cert
@@ -162,44 +167,64 @@
             }
             serviceViewModel.refresh = function () {
                 serviceViewModel.loading = true;
-                monitoringService.getDeviceList().then(function (resp) {
+                let isDeviceAdmin = $scope.role_info.role_id !== null && $scope.role_info.role_id !== '0';
+                let realServiceList = []
+                roleMgmtService.getRoleDeviceGroupMapping($scope.role_info).then(function (res) {
+                    let deviceGMap = res.data[1]['result'];
                     var deviceMap = {}
-                    _.each(resp, function (host) {
-                        deviceMap[host.ip] = host;
-                    })
-
-                    var query = 'select last(rsCntOfReq), last(rsConnPerSec), last(rsInBytePerSec)*8, last(rsOutBytePerSec)*8 from realStats where time > now()-20s group by realServerId, agent_host, Addr, Port, Protocol, Status;'
-                    dashboardService.influxdb_proxy({ "q": query }).then(function (res) {
-                        serviceViewModel.loading = false;
-                        if (res && res.status == 200) {
-                            var realServiceList = []
-                            _.each(res.data.results[0].series, function (series) {
-                                var device_ip = series.tags.agent_host;
-                                if (deviceMap[device_ip]) {
-                                    realServiceList.push({
-                                        "name": series.tags.realServerId,
-                                        "origin_type": "SLB_rs",
-                                        "type": protocol2type[series.tags.Protocol],
-                                        "addr": series.tags.Addr,
-                                        "port": series.tags.Port,
-                                        "health_status": series.tags.Status,
-                                        "device": {
-                                            "name": deviceMap[device_ip].name,
-                                            "type": deviceMap[device_ip].type,
-                                            "id": deviceMap[device_ip].id,
-                                            "ip": device_ip,
-                                            "device_group": deviceMap[device_ip].device_group,
-                                        },
-                                        "graph_data": {
-                                            "request": series.values[0][1],
-                                            "conn": series.values[0][2],
-                                            "received": storageService.ValueFormat1024(series.values[0][3]) + 'bps',
-                                            "sent": storageService.ValueFormat1024(series.values[0][4]) + 'bps',
-                                        }
-                                    })
+                    let agentHost = '';
+                    deviceGMap.forEach(function (deviceGroup) {
+                        agentHost = '';
+                        deviceGroup['device_list'].forEach(function (device) {
+                            deviceMap[device.ip] = device;
+                            if (agentHost === '') {
+                                agentHost = agentHost + '/' + device.ip;
+                            } else {
+                                agentHost = agentHost + '|' + device.ip;
+                            }
+                        })
+                        if (agentHost !== '') agentHost += '/';
+                        let query = 'select last(rsCntOfReq), last(rsConnPerSec), last(rsInBytePerSec)*8, last(rsOutBytePerSec)*8 from realStats where time > now()-20s group by realServerId, agent_host, Addr, Port, Protocol, Status;'
+                        if (isDeviceAdmin) {
+                            query = 'select last(rsCntOfReq), last(rsConnPerSec), last(rsInBytePerSec)*8, last(rsOutBytePerSec)*8 from realStats where agent_host  =~ ' + agentHost + ' and time > now()-20s group by realServerId, agent_host, Addr, Port, Protocol, Status;'
+                        }
+                        if ((isDeviceAdmin && agentHost !== '') || !isDeviceAdmin) {
+                            dashboardService.influxdb_proxy({"q": query}).then(function (res) {
+                                serviceViewModel.loading = false;
+                                if (res && res.status === 200) {
+                                    if (res.data.results.length > 0) {
+                                        _.each(res.data.results[0].series, function (series) {
+                                            var device_ip = series.tags.agent_host;
+                                            if (deviceMap[device_ip]) {
+                                                realServiceList.push({
+                                                    "name": series.tags.realServerId,
+                                                    "origin_type": "SLB_rs",
+                                                    "type": protocol2type[series.tags.Protocol],
+                                                    "addr": series.tags.Addr,
+                                                    "port": series.tags.Port,
+                                                    "health_status": series.tags.Status,
+                                                    "device": {
+                                                        "name": deviceMap[device_ip].name,
+                                                        "type": deviceMap[device_ip].type,
+                                                        "id": deviceMap[device_ip].id,
+                                                        "ip": device_ip,
+                                                        "device_group": deviceMap[device_ip].device_group,
+                                                    },
+                                                    "graph_data": {
+                                                        "request": series.values[0][1],
+                                                        "conn": series.values[0][2],
+                                                        "received": storageService.ValueFormat1024(series.values[0][3]) + 'bps',
+                                                        "sent": storageService.ValueFormat1024(series.values[0][4]) + 'bps',
+                                                    }
+                                                })
+                                            }
+                                        })
+                                    }
+                                    serviceViewModel.serviceList = realServiceList;
                                 }
-                            })
-                            serviceViewModel.serviceList = realServiceList;
+                            });
+                        } else {
+                            serviceViewModel.loading = false;
                         }
                     });
                 })
@@ -226,7 +251,7 @@
             var modalViewModel = this;
             modalViewModel.tab = "Basic Monitoring";
             modalViewModel.tabs = [
-                { name: "Basic Monitoring" },
+                {name: "Basic Monitoring"},
                 // { name: "Audit Monitoring" },
                 // { name: "Alert Rules" }
             ]
@@ -288,7 +313,7 @@
             }
 
             modalViewModel.setAlert = function (row_widget) {
-                $state.go('index.monitoring.alerting.rule.threshold.detail', { id: 0, name: "*new" });
+                $state.go('index.monitoring.alerting.rule.threshold.detail', {id: 0, name: "*new"});
                 return
                 var conditionList = [];
                 var alarmConditions = [];
@@ -375,7 +400,7 @@
                                 "conditions": [{
                                     "query": {
                                         "model": {
-                                            "tags": [{ "value": $stateParams.device_ip }, { "value": $scope.current_service_name }]
+                                            "tags": [{"value": $stateParams.device_ip}, {"value": $scope.current_service_name}]
                                         }
                                     }
                                 }],
Index: /branches/amp_3_6_0_role/extensions/monitoring/webui/resource/slb/virtual_service.controller.js
===================================================================
--- /branches/amp_3_6_0_role/extensions/monitoring/webui/resource/slb/virtual_service.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/extensions/monitoring/webui/resource/slb/virtual_service.controller.js	(working copy)
@@ -12,9 +12,10 @@
         'monitorResourceService',
         'storageService',
         'localStorageService',
-        function ($scope, $rootScope, $state, $stateParams, $location, $uibModal, $filter, dashboardService, monitoringService, monitorResourceService, storageService, localStorageService) {
+        'roleMgmtService',
+        function ($scope, $rootScope, $state, $stateParams, $location, $uibModal, $filter, dashboardService, monitoringService, monitorResourceService, storageService, localStorageService, roleMgmtService) {
             var serviceViewModel = this;
-
+            $scope.role_info = localStorageService.getWebStorage('role_info');
             $scope.currentPageIndex = 1;
             $scope.pageSize = 15;
             $scope.onPageChange = function (newPage) {
@@ -22,11 +23,11 @@
             };
 
             $scope.multiSelectData = [
-                { id: 1, label: $filter('T')("Hits Number") },
-                { id: 2, label: $filter('T')("Open Connections") },
-                { id: 3, label: $filter('T')("Received") },
-                { id: 4, label: $filter('T')("Sent") },
-                { id: 5, label: $filter('T')("Certificate Status") },
+                {id: 1, label: $filter('T')("Hits Number")},
+                {id: 2, label: $filter('T')("Open Connections")},
+                {id: 3, label: $filter('T')("Received")},
+                {id: 4, label: $filter('T')("Sent")},
+                {id: 5, label: $filter('T')("Certificate Status")},
             ];
 
             var columnVisible = localStorageService.getWebStorage("TABLE_CUSTOM_COLUMN_VISIBLE");
@@ -36,7 +37,7 @@
             if (columnVisible.vsMonitor) {
                 $scope.multiSelectModel = columnVisible.vsMonitor;
             } else {
-                $scope.multiSelectModel = [{ id: 3 }, { id: 4 }];
+                $scope.multiSelectModel = [{id: 3}, {id: 4}];
             }
             $scope.multiSelectSettings = {
                 showCheckAll: false,
@@ -98,11 +99,16 @@
 
             serviceViewModel.gridColSpan = 7;
             serviceViewModel.listType = "SLB_vs";
-            var get_adc_ssl_cert = function () {
+            let get_adc_ssl_cert = function () {
                 serviceViewModel.adc_ssl_cert_map = undefined;
-                var adc_ssl_cert_map = {};
-                monitorResourceService.get_adc_ssl_cert().then(function (res) {
-                    if (res && res.status == 200) {
+                let roleId = $scope.role_info.role_id;
+                if (roleId === null) {
+                    roleId = '0';
+                }
+                serviceViewModel.vpn_ssl_cert_map = undefined;
+                let adc_ssl_cert_map = {};
+                monitorResourceService.get_adc_ssl_cert(roleId).then(function (res) {
+                    if (res && res.status === 200) {
                         if (res.data.state) {
                             _.each(res.data.data, function (cert) {
                                 adc_ssl_cert_map[cert.device_name + '-' + cert.service_name] = cert
@@ -162,45 +168,67 @@
             }
             serviceViewModel.refresh = function () {
                 serviceViewModel.loading = true;
-                monitoringService.getDeviceList().then(function (resp) {
-                    var deviceMap = {}
-                    _.each(resp, function (host) {
-                        deviceMap[host.ip] = host;
-                    })
-                    var query = 'select max(totalHits)-min(totalHits), last(ConnCnt), last(InBytePerSec)*8, last(OutBytePerSec)*8 from virtualStats where time > now()-20s group by ServerId, agent_host, Addr, Port, Protocol, HealthStatus;'
-                    dashboardService.influxdb_proxy({ "q": query }).then(function (res) {
-                        serviceViewModel.loading = false;
-                        if (res && res.status == 200) {
-                            var virtualServiceList = []
-                            _.each(res.data.results[0].series, function (series) {
-                                var device_ip = series.tags.agent_host;
-                                if (deviceMap[device_ip]) {
-                                    virtualServiceList.push({
-                                        "name": series.tags.ServerId,
-                                        "origin_type": "SLB_vs",
-                                        "type": protocol2type[series.tags.Protocol],
-                                        "addr": series.tags.Addr,
-                                        "port": series.tags.Port,
-                                        "health_status": series.tags.HealthStatus,
-                                        "device": {
-                                            "name": deviceMap[device_ip].name,
-                                            "type": deviceMap[device_ip].type,
-                                            "id": deviceMap[device_ip].id,
-                                            "ip": device_ip,
-                                            "device_group": deviceMap[device_ip].device_group,
-                                        },
-                                        "graph_data": {
-                                            "hits": series.values[0][1],
-                                            "conn": series.values[0][2],
-                                            "received": storageService.ValueFormat1024(series.values[0][3]) + 'bps',
-                                            "sent": storageService.ValueFormat1024(series.values[0][4]) + 'bps',
-                                        }
-                                    })
+                let isDeviceAdmin = $scope.role_info.role_id !== null && $scope.role_info.role_id !== '0';
+                let virtualServiceList = []
+                roleMgmtService.getRoleDeviceGroupMapping($scope.role_info).then(function (res) {
+                    let deviceGMap = res.data[1]['result'];
+                    let deviceMap = {}
+                    let agentHost = '';
+                    deviceGMap.forEach(function (deviceGroup) {
+                        agentHost = '';
+                        deviceGroup['name'] = deviceGroup['group_name'];
+                        deviceGroup['device_list'].forEach(function (device) {
+                            deviceMap[device.ip] = device;
+                            if (agentHost === '') {
+                                agentHost = agentHost + '/' + device.ip;
+                            } else {
+                                agentHost = agentHost + '|' + device.ip;
+                            }
+                        });
+                        if (agentHost !== '') agentHost += '/';
+                        let query = 'select max(totalHits)-min(totalHits), last(ConnCnt), last(InBytePerSec)*8, last(OutBytePerSec)*8 from virtualStats where time > now()-20s group by ServerId, agent_host, Addr, Port, Protocol, HealthStatus;'
+                        if (isDeviceAdmin) {
+                            query = 'select max(totalHits)-min(totalHits), last(ConnCnt), last(InBytePerSec)*8, last(OutBytePerSec)*8 from virtualStats where agent_host  =~ ' + agentHost + ' and time > now()-20s group by ServerId, agent_host, Addr, Port, Protocol, HealthStatus;'
+                        }
+                        if ((isDeviceAdmin && agentHost !== '') || !isDeviceAdmin) {
+                            dashboardService.influxdb_proxy({"q": query}).then(function (res) {
+                                serviceViewModel.loading = false;
+                                if (res && res.status === 200) {
+                                    if (res.data.results.length > 0) {
+                                        _.each(res.data.results[0].series, function (series) {
+                                            var device_ip = series.tags.agent_host;
+                                            if (deviceMap[device_ip]) {
+                                                virtualServiceList.push({
+                                                    "name": series.tags.ServerId,
+                                                    "origin_type": "SLB_vs",
+                                                    "type": protocol2type[series.tags.Protocol],
+                                                    "addr": series.tags.Addr,
+                                                    "port": series.tags.Port,
+                                                    "health_status": series.tags.HealthStatus,
+                                                    "device": {
+                                                        "name": deviceMap[device_ip].name,
+                                                        "type": deviceMap[device_ip].type,
+                                                        "id": deviceMap[device_ip].id,
+                                                        "ip": device_ip,
+                                                        "device_group": deviceMap[device_ip].device_group,
+                                                    },
+                                                    "graph_data": {
+                                                        "hits": series.values[0][1],
+                                                        "conn": series.values[0][2],
+                                                        "received": storageService.ValueFormat1024(series.values[0][3]) + 'bps',
+                                                        "sent": storageService.ValueFormat1024(series.values[0][4]) + 'bps',
+                                                    }
+                                                })
+                                            }
+                                        })
+                                    }
+                                    serviceViewModel.serviceList = virtualServiceList;
                                 }
-                            })
-                            serviceViewModel.serviceList = virtualServiceList;
+                            });
+                        } else {
+                            serviceViewModel.loading = false;
                         }
-                    });
+                    })
                 })
             }
             serviceViewModel.refresh();
@@ -225,14 +253,14 @@
             var modalViewModel = this;
             modalViewModel.tab = "Basic Monitoring";
             modalViewModel.tabs = [
-                { name: "Basic Monitoring" },
+                {name: "Basic Monitoring"},
                 // { name: "Audit Monitoring" },
                 // { name: "Alert Rules" }
             ]
 
             var enableAudit = (angular.module("cmApp").requires.indexOf('cm.auditing') != -1)
             if (enableAudit) {
-                modalViewModel.tabs.push({ name: "Audit Monitoring" });
+                modalViewModel.tabs.push({name: "Audit Monitoring"});
             }
             var lastTab = "";
             $scope.changeTab = function (name) {
@@ -244,6 +272,7 @@
             }
             modalViewModel.vsInfo = undefined;
             modalViewModel.display_url_monitor = false;
+
             function url_escape(url) {
                 var chr_list = ['(', ')', '[', ']', ':', '\\', '/']
                 var rst = "";
@@ -303,26 +332,50 @@
                                                             {
                                                                 "id": "2",
                                                                 "type": "filters",
-                                                                "settings": { "filters": [{ "query": "tag.remote_ip:" + $stateParams.device_ip, "label": "agent_host:" + $stateParams.device_ip }] }
+                                                                "settings": {
+                                                                    "filters": [{
+                                                                        "query": "tag.remote_ip:" + $stateParams.device_ip,
+                                                                        "label": "agent_host:" + $stateParams.device_ip
+                                                                    }]
+                                                                }
                                                             },
                                                             {
                                                                 "id": "3",
                                                                 "type": "filters",
-                                                                "settings": { "filters": [{ "query": "adc.vs_name:" + $scope.current_service_name, "label": "server_id:" + $scope.current_service_name }] }
+                                                                "settings": {
+                                                                    "filters": [{
+                                                                        "query": "adc.vs_name:" + $scope.current_service_name,
+                                                                        "label": "server_id:" + $scope.current_service_name
+                                                                    }]
+                                                                }
                                                             },
                                                             {
                                                                 "id": "4",
                                                                 "type": "filters",
-                                                                "settings": { "filters": [{ "query": "adc.url:" + url_escape(url), "label": "-" }] }
+                                                                "settings": {
+                                                                    "filters": [{
+                                                                        "query": "adc.url:" + url_escape(url),
+                                                                        "label": "-"
+                                                                    }]
+                                                                }
                                                             },
                                                             {
                                                                 "id": "5",
                                                                 "type": "filters",
-                                                                "settings": { "filters": [{ "query": "tag.header:APP-HTTP", "label": $filter('T')("Response Time") }] }
+                                                                "settings": {
+                                                                    "filters": [{
+                                                                        "query": "tag.header:APP-HTTP",
+                                                                        "label": $filter('T')("Response Time")
+                                                                    }]
+                                                                }
                                                             },
-                                                            { "type": "date_histogram", "field": "@timestamp", "id": "1" }
+                                                            {"type": "date_histogram", "field": "@timestamp", "id": "1"}
                                                         ],
-                                                        "metrics": [{ "type": "avg", "field": "adc.responsetime", "id": "0" }]
+                                                        "metrics": [{
+                                                            "type": "avg",
+                                                            "field": "adc.responsetime",
+                                                            "id": "0"
+                                                        }]
                                                     }]
                                                 }
                                             }
@@ -417,7 +470,7 @@
             }
 
             modalViewModel.setAlert = function (row_widget) {
-                $state.go('index.monitoring.alerting.rule.threshold.detail', { id: 0, name: "*new" });
+                $state.go('index.monitoring.alerting.rule.threshold.detail', {id: 0, name: "*new"});
                 return
                 var conditionList = [];
                 var alarmConditions = [];
@@ -504,7 +557,7 @@
                                 "conditions": [{
                                     "query": {
                                         "model": {
-                                            "tags": [{ "value": $stateParams.device_ip }, { "value": $scope.current_service_name }]
+                                            "tags": [{"value": $stateParams.device_ip}, {"value": $scope.current_service_name}]
                                         }
                                     }
                                 }],
@@ -532,7 +585,7 @@
                 // });
             }
             var query = 'select last(ConnCnt) from virtualStats where time > now()-20s and ServerId=\'' + $scope.current_service_name + '\' and agent_host=\'' + $stateParams.device_ip + '\' group by ServerId, agent_host, Addr, Port, Protocol;'
-            dashboardService.influxdb_proxy({ "q": query }).then(function (res) {
+            dashboardService.influxdb_proxy({"q": query}).then(function (res) {
                 if (res && res.status == 200) {
                     if (res.data.results[0].series.length == 1) {
                         series = res.data.results[0].series[0];
Index: /branches/amp_3_6_0_role/extensions/monitoring/webui/resource/sslvpn/sslvpn.controller.js
===================================================================
--- /branches/amp_3_6_0_role/extensions/monitoring/webui/resource/sslvpn/sslvpn.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/extensions/monitoring/webui/resource/sslvpn/sslvpn.controller.js	(working copy)
@@ -11,9 +11,10 @@
         'monitorResourceService',
         'dashboardService',
         'localStorageService',
-        function ($scope, $rootScope, $state, $stateParams, $location, $uibModal, $filter, monitoringService, monitorResourceService, dashboardService, localStorageService) {
+        'roleMgmtService',
+        function ($scope, $rootScope, $state, $stateParams, $location, $uibModal, $filter, monitoringService, monitorResourceService, dashboardService, localStorageService, roleMgmtService) {
             $rootScope.title = 'SSLVPN Services';
-
+            $scope.role_info = localStorageService.getWebStorage('role_info');
             var serviceViewModel = this;
 
             $scope.currentPageIndex = 1;
@@ -23,8 +24,8 @@
             };
 
             $scope.multiSelectData = [
-                { id: 1, label: $filter('T')("Sessions Number") },
-                { id: 2, label: $filter('T')("Certificate Status") },
+                {id: 1, label: $filter('T')("Sessions Number")},
+                {id: 2, label: $filter('T')("Certificate Status")},
             ];
 
             var columnVisible = localStorageService.getWebStorage("TABLE_CUSTOM_COLUMN_VISIBLE");
@@ -34,7 +35,7 @@
             if (columnVisible.sslvpnMonitor) {
                 $scope.multiSelectModel = columnVisible.sslvpnMonitor;
             } else {
-                $scope.multiSelectModel = [{ id: 1 }];
+                $scope.multiSelectModel = [{id: 1}];
             }
             $scope.multiSelectSettings = {
                 showCheckAll: false,
@@ -87,11 +88,15 @@
 
             serviceViewModel.gridColSpan = 5;
 
-            var get_vpn_ssl_cert = function () {
+            let get_vpn_ssl_cert = function () {
+                let roleId = $scope.role_info.role_id;
+                if (roleId === null) {
+                    roleId = '0';
+                }
                 serviceViewModel.vpn_ssl_cert_map = undefined;
-                var vpn_ssl_cert_map = {};
-                monitorResourceService.get_vpn_ssl_cert().then(function (res) {
-                    if (res && res.status == 200) {
+                let vpn_ssl_cert_map = {};
+                monitorResourceService.get_vpn_ssl_cert(roleId).then(function (res) {
+                    if (res && res.status === 200) {
                         if (res.data.state) {
                             _.each(res.data.data, function (cert) {
                                 vpn_ssl_cert_map[cert.device_name + '-' + cert.service_name] = cert
@@ -131,41 +136,60 @@
 
             serviceViewModel.refresh = function () {
                 serviceViewModel.loading = true;
-                monitoringService.getDeviceList().then(function (resp) {
-                    var deviceMap = {}
-                    _.each(resp, function (host) {
-                        deviceMap[host.ip] = host;
-                    })
-
-                    var query = 'select last(ActiveSessions) from virtualSiteStats where time > now()-20s group by Id, agent_host, IP;'
-                    dashboardService.influxdb_proxy({ "q": query }).then(function (res) {
-                        serviceViewModel.loading = false;
-                        if (res && res.status == 200) {
-                            var virtualSiteList = []
-                            _.each(res.data.results[0].series, function (series) {
-                                var device_ip = series.tags.agent_host;
-                                if (deviceMap[device_ip]) {
-                                    virtualSiteList.push({
-                                        "name": series.tags.Id,
-                                        "origin_type": "SSLVPN",
-                                        "ip": series.tags.IP,
-                                        "device": {
-                                            "name": deviceMap[device_ip].name,
-                                            "type": deviceMap[device_ip].type,
-                                            "id": deviceMap[device_ip].id,
-                                            "ip": device_ip,
-                                            "device_group": deviceMap[device_ip].device_group,
-                                        },
-                                        "graph_data": {
-                                            "sessions": series.values[0][1],
-                                        }
-                                    })
+                let agentHost = '';
+                let isDeviceAdmin = $scope.role_info.role_id !== null && $scope.role_info.role_id !== '0';
+                let virtualSiteList = [];
+                roleMgmtService.getRoleDeviceGroupMapping($scope.role_info).then(function (resp) {
+                    let deviceMap = {}
+                    resp.data[1]['result'].forEach(function (deviceGroup) {
+                        let agentHost = '';
+                        _.each(deviceGroup['device_list'], function (host) {
+                            deviceMap[host.ip] = host;
+                            if (agentHost === '') {
+                                agentHost = agentHost + '/' + host.ip;
+                            } else {
+                                agentHost = agentHost + '|' + host.ip;
+                            }
+                        })
+                        if (agentHost !== '') agentHost += '/';
+                        let query = 'select last(ActiveSessions) from virtualSiteStats where time > now()-20s group by Id, agent_host, IP;'
+                        if (isDeviceAdmin) {
+                            query = 'select last(ActiveSessions) from virtualSiteStats where agent_host  =~ ' + agentHost + ' and time > now()-20s group by Id, agent_host, IP;'
+                        }
+                        if ((isDeviceAdmin && agentHost !== '') || !isDeviceAdmin) {
+                            dashboardService.influxdb_proxy({"q": query}).then(function (res) {
+                                serviceViewModel.loading = false;
+                                if (res && res.status === 200) {
+                                    if (res.data.results.length > 0) {
+                                        _.each(res.data.results[0].series, function (series) {
+                                            let device_ip = series.tags.agent_host;
+                                            if (deviceMap[device_ip]) {
+                                                virtualSiteList.push({
+                                                    "name": series.tags.Id,
+                                                    "origin_type": "SSLVPN",
+                                                    "ip": series.tags.IP,
+                                                    "device": {
+                                                        "name": deviceMap[device_ip].name,
+                                                        "type": deviceMap[device_ip].type,
+                                                        "id": deviceMap[device_ip].id,
+                                                        "ip": device_ip,
+                                                        "device_group": deviceMap[device_ip].device_group,
+                                                    },
+                                                    "graph_data": {
+                                                        "sessions": series.values[0][1],
+                                                    }
+                                                })
+                                            }
+                                        })
+                                    }
+                                    serviceViewModel.serviceList = virtualSiteList;
                                 }
-                            })
-                            serviceViewModel.serviceList = virtualSiteList;
+                            });
+                        } else {
+                            serviceViewModel.loading = false;
                         }
-                    });
-                })
+                    })
+                });
             }
 
             serviceViewModel.refresh();
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/admin.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/admin.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/admin.controller.js	(working copy)
@@ -1,21 +1,18 @@
 angular.module('cm.admin')
-	.controller('adminCtrl', [
-		'$rootScope',
-		'$scope',
-		'$state',
-		'$stateParams',
-		'$uibModal',
-		'$filter',
-		'$location',
-		function ($rootScope, $scope, $state, $stateParams, $uibModal, $filter, $location) {
+    .controller('adminCtrl', [
+        '$rootScope',
+        '$scope',
+        '$state',
+        '$stateParams',
+        '$uibModal',
+        '$filter',
+        '$location',
+        'localStorageService',
+        function ($rootScope, $scope, $state, $stateParams, $uibModal, $filter, $location, localStorageService) {
+            $scope.role_info = localStorageService.getWebStorage('role_info');
             $scope.url_contain = function (url) {
-                if ($location.path().indexOf(url) > -1) {
-                    return true;
-                } else {
-                    return false;
-                }
+                return $location.path().indexOf(url) > -1;
             }
-
-			$rootScope.title = 'Administrator';
-		}
-	]);
+            $rootScope.title = 'Administrator';
+        }
+    ]);
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/admin.module.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/admin.module.js	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/admin.module.js	(working copy)
@@ -12,6 +12,9 @@
                         controller:'adminCtrl',
                         controllerAs:'admin'
                     }
+                },
+                ncyBreadcrumb: {
+                    label: '{{ "System Administrator" | T }}'
                 }
             })
             .state('index.admin.userMgmt', {
@@ -27,6 +30,33 @@
                     label: '{{ "System Administrator" | T }}'
                 }
             })
+            .state('index.admin.roleMgmt', {
+                url: '^/admin/roleMgmt',
+                views: {
+                    'roleMgmt@index.admin': {
+                        templateUrl: 'app/modules/administrator/roleMgmt/roleMgmt.html',
+                        controller: 'roleMgmtCtrl',
+                        controllerAs: 'roleMgmt'
+                    }
+                },
+                ncyBreadcrumb: {
+                    label: '{{ "Role" | T }}'
+                }
+            })
+            .state('index.admin.roleMgmt.deviceGroupMap', {
+                url: '^/admin/roleMgmt/detail/{name}',
+                views: {
+                    'main@index': {
+                        templateUrl: 'app/modules/administrator/roleMgmt/detail/role-device-group-mapping.html',
+                        controller: 'roleDeviceGroupMapCtrl',
+                        controllerAs: 'roleDeviceGroupMap'
+                    }
+                },
+                ncyBreadcrumb: {
+                    parent: 'index.admin.roleMgmt',
+                    label: '{{current_name}}',
+                }
+            })
             .state('index.admin.operLog', {
                 url: '^/admin/operLog',
                 views: {
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/index.html
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/index.html	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/index.html	(working copy)
@@ -4,6 +4,10 @@
             <li role="presentation" ng-class="{ active: url_contain('/admin/userMgmt') }">
                 <a ui-sref="index.admin.userMgmt">{{ 'System Administrator' | T }}</a>
             </li>
+            <li role="presentation" ng-if="role_info.user_type !== 'Device Admin'"
+                ng-class="{ active: url_contain('/admin/roleMgmt') }">
+                <a ui-sref="index.admin.roleMgmt">{{ 'User Role' | T }}</a>
+            </li>
             <li role="presentation" ng-class="{ active: url_contain('/admin/operLog') }">
                 <a ui-sref="index.admin.operLog">{{ 'Operation Log' | T }}</a>
             </li>
@@ -15,6 +19,7 @@
     <br>
     <div class="">
         <div class="" ng-show="url_contain('/admin/userMgmt')" ui-view="userMgmt"></div>
+        <div class="" ng-show="url_contain('/admin/roleMgmt')" ui-view="roleMgmt"></div>
         <div class="" ng-show="url_contain('/admin/operLog')" ui-view="operLog"></div>
         <div class="" ng-show="url_contain('/admin/systemAction')" ui-view="systemAction"></div>
     </div>
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/detail/role-device-group-mapping.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/detail/role-device-group-mapping.controller.js	(revision 0)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/detail/role-device-group-mapping.controller.js	(working copy)
@@ -0,0 +1,154 @@
+angular.module('cm.admin')
+    .controller('roleDeviceGroupMapCtrl', ['$scope', '$rootScope', '$state', '$stateParams', '$location', '$uibModal', '$aside', 'roleMgmtService', '$filter', 'localStorageService', 'FileUploader', '$timeout', 'deviceService', function ($scope, $rootScope, $state, $stateParams, $location, $uibModal, $aside, roleMgmtService, $filter, localStorageService, FileUploader, $timeout, deviceService) {
+        let roleDeviceGroupMapModel = this;
+        roleDeviceGroupMapModel.deviceGroupList = [];
+        roleDeviceGroupMapModel.deviceMap = [];
+        $scope.role_info = localStorageService.getWebStorage('role_info');
+        $rootScope.current_name = $stateParams.name;
+        $rootScope.title = $stateParams.name;
+
+        $scope.current_name = $stateParams.name;
+
+        function getDeviceGroupMapping() {
+            // fetch all the device groups and its devices
+            let roleInfo = {role_id: '0'};
+            roleDeviceGroupMapModel.deviceGroupsMap = [];
+            roleMgmtService.getRoleDeviceGroupMapping(roleInfo).then(function (res) {
+                if (res && res.status === 200) {
+                    try {
+                        let data = res.data;
+                        if (data.length > 1) {
+                            try {
+                                roleDeviceGroupMapModel.deviceGroupsMap = data[1]['result'];
+                            } catch (e) {
+                                console.error('Error getDeviceGroupMapping returned error.' + e);
+                                roleDeviceGroupMapModel.deviceGroupsMap = [];
+                            }
+                        }
+                    } catch (e) {
+                        console.log('500 - Internal server error.');
+                        alert('500 - Internal server error. Failed to fetch device group mapping info.');
+                    }
+                }
+            });
+        }
+
+        function getRoleDeviceGroupMapping() {
+            let roleInfo = JSON.parse(window.localStorage.__roleInfo__);
+            roleDeviceGroupMapModel.deviceMap = [];
+            roleDeviceGroupMapModel.deviceGroupList = [];
+            $rootScope.roleInfo = roleInfo;
+            // fetch the device group information for the specific role.
+            roleMgmtService.getRoleDeviceGroupMapping(roleInfo).then(function (res) {
+                if (res && res.status === 200) {
+                    try {
+                        let data = res.data;
+                        if (data.length > 1) {
+                            try {
+                                let deviceMap = data[1]['result'];
+                                roleDeviceGroupMapModel.deviceGroupList = deviceMap;
+                                $scope.group_list = [];
+                                deviceMap.forEach(function (deviceGroup) {
+                                    let device_list = '';
+                                    $scope.group_list.push(deviceGroup['group_name']);
+                                    deviceGroup['device_list'].forEach(function (device) {
+                                        if (device_list !== '') {
+                                            device_list += ', '
+                                        }
+                                        device_list += device.ip;
+                                    })
+                                    roleDeviceGroupMapModel.deviceMap.push({
+                                        group_name: deviceGroup['group_name'], device_list: device_list
+                                    })
+                                })
+                            } catch (e) {
+                                console.error('Error getRoleDeviceGroupMapping returned error.' + e);
+                                roleDeviceGroupMapModel.deviceMap = [];
+                            }
+                        }
+                    } catch (e) {
+                        console.log('500 - Internal server error.');
+                        alert('500 - Internal server error. Failed to fetch device group mapping info.');
+                    }
+                }
+            });
+        }
+
+        roleDeviceGroupMapModel.refresh = function () {
+            getDeviceGroupMapping();
+            getRoleDeviceGroupMapping();
+        }
+
+        roleDeviceGroupMapModel.manageDeviceGroup = function () {
+            if (roleDeviceGroupMapModel.deviceMap === undefined) {
+                roleDeviceGroupMapModel.deviceMap = [];
+            }
+            let modalInstance = $uibModal.open({
+                templateUrl: 'app/modules/administrator/roleMgmt/modal/role-device-group-manage.html',
+                controller: 'roleDeviceGroupManageCtrl',
+                controllerAs: 'roleDeviceGroupManage',
+                resolve: {
+                    modalData: {
+                        deviceGroup: roleDeviceGroupMapModel.deviceGroupList,
+                        deviceGroupsMap: roleDeviceGroupMapModel.deviceGroupsMap,
+                        selectedGroups: $scope.group_list,
+                        roleInfo: $rootScope.roleInfo
+                    }
+                }
+            });
+            modalInstance.result.then(function (selectedGroups) {
+                let payload = {
+                    role_id: $rootScope.roleInfo['role_id'],
+                    groups: selectedGroups,
+                }
+                roleMgmtService.updateRoleDeviceGroupMapping(payload).then(function (res) {
+                    if (res && res.status === 200) {
+                        roleDeviceGroupMapModel.refresh();
+                    } else {
+                        console.log('500 - Internal server error.');
+                        alert('500 - Internal server error. Failed to update the device group mapping info.');
+                    }
+                });
+            });
+        }
+
+        roleDeviceGroupMapModel.removeDeviceGroup = function (deviceGroup) {
+            let modalInstance = $uibModal.open({
+                templateUrl: 'app/modules/administrator/roleMgmt/modal/role-device-group-del.html',
+                controller: 'roleDeviceGroupDelController',
+                controllerAs: 'roleDeviceGroupDel',
+                resolve: {
+                    delInfo: function () {
+                        return deviceGroup.group_name;
+                    }
+                }
+            });
+            modalInstance.result.then(function (deviceGroupName) {
+                if (deviceGroupName) {
+                    let newDeviceGroup = $scope.group_list;
+                    newDeviceGroup = newDeviceGroup.filter(item => item !== deviceGroupName);
+                    let payload = {
+                        role_id: $rootScope.roleInfo['role_id'],
+                        groups: newDeviceGroup,
+                    }
+                    roleMgmtService.updateRoleDeviceGroupMapping(payload).then(function (res) {
+                        if (res && res.status === 200) {
+                            roleDeviceGroupMapModel.refresh();
+                        } else {
+                            console.log('500 - Internal server error.');
+                            alert('500 - Internal server error. Failed to update the device group mapping info.');
+                        }
+                    });
+                }
+            });
+        }
+
+        getDeviceGroupMapping();
+        getRoleDeviceGroupMapping();
+
+        $scope.currentPageIndex = 1;
+        $scope.pageSize = 15;
+        $scope.onPageChange = function (newPage) {
+            $scope.currentPageIndex = newPage;
+        };
+    }])
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/detail/role-device-group-mapping.html
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/detail/role-device-group-mapping.html	(revision 0)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/detail/role-device-group-mapping.html	(working copy)
@@ -0,0 +1,56 @@
+<div>
+    <div class="row">
+        <div class="col-md-12">
+            <div ncy-breadcrumb></div>
+            <div class="table-toolbar">
+                <div class="btn-group">
+                    <button class="btn btn-link" title="{{ 'Refresh' | T }}" ng-click="roleDeviceGroupMap.refresh()"><i
+                        class="fa fa-refresh"></i></button>
+                    <button ng-if="role_info.user_type === 'Super Admin'" class="btn btn-link" title="{{ 'Add' | T }}" ng-click="roleDeviceGroupMap.manageDeviceGroup()"><i
+                        class="fa fa-edit"></i></button>
+                </div>
+            </div>
+            <div class="tab-wrapper">
+                <ul class="nav nav-tabs">
+                    <li role="presentation">
+                        <a>{{ roleInfo["name"] }} - {{'Device Permission' | T }}</a>
+                    </li>
+                </ul>
+            </div>
+            <div class="table-wrapper">
+                <table st-table="deviceMap" st-safe-src="roleDeviceGroupMap.deviceMap"
+                       class="table table-hover table-striped">
+                    <thead>
+                    <tr>
+                        <th class="d-num">No.</th>
+                        <th class="d-name">{{ 'Device Group Name' | T }}</th>
+                        <th class="d-name">{{ 'Managed Devices' | T }}</th>
+                        <th class="d-action">{{ 'Action' | T }}</th>
+                    </tr>
+                    </thead>
+                    <tbody>
+                    <tr ng-repeat="deviceGroup in deviceMap">
+                        <td>{{ $index + 1 }}</td>
+                        <td class="d-name">{{deviceGroup.group_name}}</td>
+                        <td class="d-name">{{deviceGroup.device_list }}</td>
+                        <td class="d-action">
+                            <button class="btn-link" title="{{ 'Delete' | T }}"
+                                    ng-if="role_info.user_type === 'Super Admin'"
+                                    ng-click="roleDeviceGroupMap.removeDeviceGroup(deviceGroup)"><i
+                                class="array-delete" style="font-size: 1.25em;"></i></button>
+                        </td>
+                    </tr>
+                    </tbody>
+                    <tfoot>
+                    <tr>
+                        <td colspan="5" class="text-center">
+                            <div st-pagination="" st-items-by-page="pageSize" st-displayed-pages="5"
+                                 st-page-change="onPageChange(newPage)"></div>
+                        </td>
+                    </tr>
+                    </tfoot>
+                </table>
+            </div>
+        </div>
+    </div>
+</div>
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-add.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-add.controller.js	(revision 0)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-add.controller.js	(working copy)
@@ -0,0 +1,66 @@
+angular.module('cm.admin')
+    .controller('roleAddController', [
+        '$scope',
+        '$rootScope',
+        '$state',
+        '$stateParams',
+        '$uibModal',
+        '$uibModalInstance',
+        '$filter',
+        'roleMgmtService',
+        'localStorageService',
+        function ($scope, $rootScope, $state, $stateParams, $uibModal, $uibModalInstance, $filter, roleMgmtService, localStorageService) {
+            var addViewModal = this;
+
+            addViewModal.showProgressBar = function () {
+                var modalInstance = $uibModal.open({
+                    templateUrl: 'app/modules/common/templates/progress.html',
+                    controller: 'showProgressCtrl',
+                    controllerAs: 'progress',
+                    backdrop: false
+                });
+            };
+
+            addViewModal.close = function () {
+                $uibModalInstance.dismiss();
+            };
+            addViewModal.submit = function () {
+                if (addViewModal.role_name === undefined || addViewModal.role_name === '') {
+                    var errorMsg = $filter('T')("{0} can't be empty!", [$filter('T')('Role Name')]);
+                    addViewModal.errorMsg = errorMsg;
+                    return;
+                } else {
+                    var name_pattern = /^[a-zA-Z_]{1}[a-zA-Z0-9_]*$/;
+                    if (!name_pattern.test(addViewModal.role_name)) {
+                        addViewModal.errorMsg = $filter('T')("Invalid {0}!", [$filter('T')('Role Name')]);
+                        return;
+                    } else if (addViewModal.role_name === 'test' || addViewModal.role_name === 'root') {
+                        addViewModal.errorMsg = $filter('T')("Invalid {0}!", [$filter('T')('Role Name')]);
+                        return;
+                    }
+                }
+                addViewModal.showProgressBar();
+                var data = {
+                    role_name: addViewModal.role_name.replace(/\s/g, "")
+                };
+
+                roleMgmtService.addRole(data).then(function (response) {
+                    $rootScope.$broadcast('endLoading', true);
+                    if (response && response.status === 200) {
+                        if (response.data && !response.data[0]) {
+                            addViewModal.errorMsg = response.data[1];
+                        } else {
+                            if (response.data[2] && angular.isArray(response.data[2])
+                                && response.data[2].length === 1 && response.data[2][0].length === 2) {
+                                addViewModal.errorMsg = $filter("T")(response.data[2][0][1]);
+                            } else {
+                                $uibModalInstance.close(true);
+                            }
+                        }
+                    } else {
+                        addViewModal.errorMsg = $filter('T')('Internal server error');
+                    }
+                });
+            };
+        }
+    ]);
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-add.html
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-add.html	(revision 0)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-add.html	(working copy)
@@ -0,0 +1,34 @@
+<div class="">
+    <div class="modal-header">
+        <button type="button" class="close" ng-click="roleAdd.close()" aria-label="Close"><span aria-hidden="true">&times;</span>
+        </button>
+        <h5 class="modal-title">{{ 'Add User Role' | T}}</h5>
+    </div>
+    <div class="modal-body">
+        <form class="form-horizontal" name="add">
+            <div class="form-group">
+                <label class="control-label col-md-3">{{ 'Role Name' | T }}</label>
+                <div class="col-md-9">
+                    <input type="text" class="form-control" ng-model="roleAdd.role_name">
+                </div>
+            </div>
+            <div class="form-group">
+                <div class="col-md-offset-3 col-md-9 errorMsg">{{roleAdd.errorMsg}}</div>
+            </div>
+            <div class="form-group">
+                <div class="col-md-offset-3 col-md-9">
+                    <button class="btn btn-primary" ng-click="roleAdd.submit()">{{ 'Create' | T}}</button>
+                    <button class="btn btn-default" ng-click="roleAdd.close()">{{ 'Cancel' | T}}</button>
+                </div>
+            </div>
+
+
+        </form>
+    </div>
+</div>
+
+<style>
+    .modal-dialog {
+        width: 700px;
+    }
+</style>
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-del.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-del.controller.js	(revision 0)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-del.controller.js	(working copy)
@@ -0,0 +1,52 @@
+angular.module('cm.admin')
+    .controller('roleDelController', [
+        '$scope',
+        '$rootScope',
+        '$state',
+        '$stateParams',
+        '$uibModal',
+        '$uibModalInstance',
+        'roleMgmtService',
+        'delInfo',
+        '$filter',
+        function ($scope, $rootScope, $state, $stateParams, $uibModal, $uibModalInstance, roleMgmtService, delInfo, $filter) {
+
+            var delViewModal = this;
+
+            delViewModal.showProgressBar = function () {
+                var modalInstance = $uibModal.open({
+                    templateUrl: 'app/modules/common/templates/progress.html',
+                    controller: 'showProgressCtrl',
+                    controllerAs: 'progress',
+                    backdrop: false
+                });
+            };
+
+            delViewModal.submit = function () {
+                delViewModal.showProgressBar();
+                roleMgmtService
+                    .deleteRole(delInfo)
+                    .then(function (response) {
+                        $rootScope.$broadcast('endLoading', true);
+                        if (response && response.status === 200) {
+                            if (response.data && !response.data[0]) {
+                                delViewModal.errorMsg = response.data[1];
+                            } else {
+                                if (response.data[2] && angular.isArray(response.data[2])
+                                    && response.data[2].length === 1 && response.data[2][0].length === 2) {
+                                    delViewModal.errorMsg = $filter("T")(response.data[2][0][1]);
+                                } else {
+                                    $uibModalInstance.close(true);
+                                }
+                            }
+                        } else {
+                            alert($filter('T')(response.data[1]));
+                        }
+                    });
+            };
+
+            delViewModal.close = function () {
+                $uibModalInstance.dismiss();
+            }
+        }
+    ]);
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-del.html
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-del.html	(revision 0)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-del.html	(working copy)
@@ -0,0 +1,19 @@
+<div class="table-delete-dialog modal-body alert-box">
+    <div class="alert-content">
+        <span>{{ 'Are you sure to perform the deletion?' | T}}</span>
+        <div class="form-group">
+            <div class="col-md errorMsg" style="word-wrap: break-word;">{{roleDel.errorMsg}}</div>
+        </div>
+    </div>
+
+    <div class="alert-btn">
+        <button class="btn btn-primary" ng-click="roleDel.submit()">{{ 'Confirm' | T}}</button>
+        <button class="btn btn-default" ng-click="roleDel.close()">{{ 'Cancel' | T}}</button>
+    </div>
+</div>
+
+<style>
+    .modal-dialog {
+        width: 544px;
+    }
+</style>
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-device-group-del.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-device-group-del.controller.js	(revision 0)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-device-group-del.controller.js	(working copy)
@@ -0,0 +1,24 @@
+angular.module('cm.admin')
+    .controller('roleDeviceGroupDelController', [
+        '$scope',
+        '$rootScope',
+        '$state',
+        '$stateParams',
+        '$uibModal',
+        '$uibModalInstance',
+        'roleMgmtService',
+        'delInfo',
+        '$filter',
+        function ($scope, $rootScope, $state, $stateParams, $uibModal, $uibModalInstance, roleMgmtService, delInfo, $filter) {
+
+            let delViewModal = this;
+
+            delViewModal.submit = function () {
+                $uibModalInstance.close(delInfo);
+            };
+
+            delViewModal.close = function () {
+                $uibModalInstance.dismiss();
+            }
+        }
+    ]);
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-device-group-del.html
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-device-group-del.html	(revision 0)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-device-group-del.html	(working copy)
@@ -0,0 +1,19 @@
+<div class="table-delete-dialog modal-body alert-box">
+    <div class="alert-content">
+        <span>{{ 'Are you sure to perform the deletion?' | T}}</span>
+        <div class="form-group">
+            <div class="col-md errorMsg" style="word-wrap: break-word;"></div>
+        </div>
+    </div>
+
+    <div class="alert-btn">
+        <button class="btn btn-primary" ng-click="roleDeviceGroupDel.submit()">{{ 'Confirm' | T}}</button>
+        <button class="btn btn-default" ng-click="roleDeviceGroupDel.close()">{{ 'Cancel' | T}}</button>
+    </div>
+</div>
+
+<style>
+    .modal-dialog {
+        width: 544px;
+    }
+</style>
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-device-group-manage.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-device-group-manage.controller.js	(revision 0)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-device-group-manage.controller.js	(working copy)
@@ -0,0 +1,17 @@
+angular.module('cm.admin')
+    .controller('roleDeviceGroupManageCtrl', ['$scope', '$rootScope', '$state', '$stateParams', '$uibModal', '$uibModalInstance', '$filter', 'roleMgmtService', 'localStorageService', 'modalData', 'deviceService', function ($scope, $rootScope, $state, $stateParams, $uibModal, $uibModalInstance, $filter, roleMgmtService, localStorageService, modalData, deviceService) {
+        var roleDeviceGroupManageModel = this;
+
+        roleDeviceGroupManageModel.showDevice = false;
+        roleDeviceGroupManageModel.modelData = modalData;
+        roleDeviceGroupManageModel.deviceGroupsMap = modalData.deviceGroupsMap;
+        roleDeviceGroupManageModel.selectedGroups = modalData.selectedGroups;
+
+        roleDeviceGroupManageModel.close = function () {
+            $uibModalInstance.dismiss();
+        };
+
+        roleDeviceGroupManageModel.save = function () {
+            $uibModalInstance.close(roleDeviceGroupManageModel.selectedGroups);
+        };
+    }])
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-device-group-manage.html
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-device-group-manage.html	(revision 0)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-device-group-manage.html	(working copy)
@@ -0,0 +1,32 @@
+<div class="modal-header">
+    <button type="button" class="close" ng-click="roleDeviceGroupManage.close()">&times;</button>
+    <h4 class="modal-title">{{'Bind Devices'|T}}</h4>
+</div>
+
+<div class="modal-body">
+    <div class="row">
+        <div class="col-lg-12">
+            <form class="form-horizontal" name="general" verify-scope="tipStyle: 1">
+                <div class="form-group">
+                    <label class="col-md-3 control-label">{{'Device Groups'|T}}</label>
+                    <div class="col-md-8" v-if="roleDeviceGroupManage.showDevice">
+                        <select ng-verify="required:true" bs-select multiple data-width="260px"
+                                class="form-control selectpicker" placeholder=""
+                                ng-model="roleDeviceGroupManage.selectedGroups">
+                            <option value="{{row.group_name}}" ng-repeat="row in roleDeviceGroupManage.deviceGroupsMap">
+                                {{ row.group_name }}
+                            </option>
+                        </select>
+                    </div>
+                </div>
+                <br><br><br>
+            </form>
+        </div>
+    </div>
+</div>
+<div class="modal-footer">
+    <button ng-verify="control:'general'" type="button" class="btn btn-primary"
+            ng-click="roleDeviceGroupManage.save()">{{'Save'|T}}
+    </button>
+    <button type="button" class="btn btn-default" ng-click="roleDeviceGroupManage.close()">{{'Cancel'|T}}</button>
+</div>
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-edit.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-edit.controller.js	(revision 0)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-edit.controller.js	(working copy)
@@ -0,0 +1,69 @@
+angular.module('cm.admin')
+    .controller('roleEditController', [
+        '$scope',
+        '$rootScope',
+        '$state',
+        '$stateParams',
+        '$uibModal',
+        '$uibModalInstance',
+        '$filter',
+        'roleMgmtService',
+        'editInfo',
+        'localStorageService',
+        function ($scope, $rootScope, $state, $stateParams, $uibModal, $uibModalInstance, $filter, roleMgmtService, editInfo, localStorageService) {
+            var editViewModal = this;
+
+            editViewModal.role_name = editInfo.role_name;
+            editViewModal.id = editInfo.id;
+
+            editViewModal.showProgressBar = function () {
+                var modalInstance = $uibModal.open({
+                    templateUrl: 'app/modules/common/templates/progress.html',
+                    controller: 'showProgressCtrl',
+                    controllerAs: 'progress',
+                    backdrop: false
+                });
+            };
+
+            editViewModal.close = function () {
+                $uibModalInstance.dismiss();
+            };
+
+            editViewModal.submit = function () {
+                if (editViewModal.role_name === undefined || editViewModal.role_name === '') {
+                    var errorMsg = $filter('T')("{0} can't be empty!", [$filter('T')('Role Name')]);
+                    editViewModal.errorMsg = errorMsg;
+                    return;
+                } else {
+                    var name_pattern = /^[a-zA-Z_]{1}[a-zA-Z0-9_]*$/;
+                    if (!name_pattern.test(editViewModal.role_name)) {
+                        editViewModal.errorMsg = $filter('T')("Invalid {0}!", [$filter('T')('Role Name')]);
+                        return;
+                    } else if (editViewModal.role_name === 'test' || editViewModal.role_name === 'root') {
+                        editViewModal.errorMsg = $filter('T')("Invalid {0}!", [$filter('T')('Role Name')]);
+                        return;
+                    }
+                }
+                editViewModal.showProgressBar();
+
+                var data = {
+                    id: editViewModal.id,
+                    role_name: editViewModal.role_name.replace(/\s/g, "")
+                };
+
+                roleMgmtService.updateRole(data).then(function (response) {
+                    $rootScope.$broadcast('endLoading', true);
+                    if (response.data && !response.data[0]) {
+                        editViewModal.errorMsg = response.data[1];
+                    } else {
+                        if (response.data[2] && angular.isArray(response.data[2])
+                            && response.data[2].length === 1 && response.data[2][0].length === 2) {
+                            editViewModal.errorMsg = $filter("T")(response.data[2][0][1]);
+                        } else {
+                            $uibModalInstance.close(true);
+                        }
+                    }
+                });
+            };
+        }
+    ]);
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-edit.html
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-edit.html	(revision 0)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/modal/role-edit.html	(working copy)
@@ -0,0 +1,32 @@
+<div class="">
+    <div class="modal-header">
+        <button type="button" class="close" ng-click="roleEdit.close()" aria-label="Close"><span aria-hidden="true">&times;</span>
+        </button>
+        <h5 class="modal-title">{{ 'Edit User Role' | T}}</h5>
+    </div>
+    <div class="modal-body">
+        <form class="form-horizontal" name="add">
+            <div class="form-group">
+                <label class="control-label col-md-3">{{ 'Role Name' | T }}</label>
+                <div class="col-md-9">
+                    <input type="text" class="form-control" ng-model="roleEdit.role_name">
+                </div>
+            </div>
+            <div class="form-group">
+                <div class="col-md-offset-3 col-md-9 errorMsg">{{roleEdit.errorMsg}}</div>
+            </div>
+            <div class="form-group">
+                <div class="col-md-offset-3 col-md-9">
+                    <button class="btn btn-primary" ng-click="roleEdit.submit()">{{ 'Update' | T}}</button>
+                    <button class="btn btn-default" ng-click="roleEdit.close()">{{ 'Cancel' | T}}</button>
+                </div>
+            </div>
+        </form>
+    </div>
+</div>
+
+<style>
+    .modal-dialog {
+        width: 700px;
+    }
+</style>
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/roleMgmt.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/roleMgmt.controller.js	(revision 0)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/roleMgmt.controller.js	(working copy)
@@ -0,0 +1,101 @@
+angular.module('cm.admin')
+    .controller('roleMgmtCtrl', [
+        '$scope',
+        '$rootScope',
+        '$state',
+        '$stateParams',
+        '$location',
+        '$uibModal',
+        '$aside',
+        'roleMgmtService',
+        '$filter',
+        'localStorageService',
+        'FileUploader',
+        '$timeout',
+        function ($scope, $rootScope, $state, $stateParams, $location, $uibModal, $aside, roleMgmtService, $filter, localStorageService, FileUploader, $timeout) {
+            $rootScope.title = 'User Role';
+            $scope.role_info = localStorageService.getWebStorage('role_info');
+
+            if ($scope.role_info.user_type === "Device Admin") {
+                $location.path('/admin/userMgmt');
+            }
+
+            let roleViewModel = this;
+
+            $scope.currentPageIndex = 1;
+            $scope.pageSize = 10;
+            $scope.onPageChange = function (newPage) {
+                $scope.currentPageIndex = newPage;
+            };
+
+            roleViewModel.roleList = undefined;
+
+            roleViewModel.refresh = function () {
+                getRoles();
+            }
+
+            function getRoles() {
+                roleViewModel.roleList = [];
+                roleMgmtService.getRoles().then(function (res) {
+                    if (res && res.status === 200) {
+                        roleViewModel.roleList = res.data;
+                    }
+                })
+            }
+
+            roleViewModel.addRole = function () {
+                let modalInstance = $uibModal.open({
+                    templateUrl: 'app/modules/administrator/roleMgmt/modal/role-add.html',
+                    controller: 'roleAddController',
+                    controllerAs: 'roleAdd',
+                    resolve: {}
+                });
+                modalInstance.result.then(function (selectedItem) {
+                    if (selectedItem) {
+                        roleViewModel.refresh();
+                    }
+                });
+            }
+
+            roleViewModel.editRole = function (role) {
+                let modalInstance = $uibModal.open({
+                    templateUrl: 'app/modules/administrator/roleMgmt/modal/role-edit.html',
+                    controller: 'roleEditController',
+                    controllerAs: 'roleEdit',
+                    resolve: {
+                        editInfo: function () {
+                            return role;
+                        }
+                    }
+                });
+                modalInstance.result.then(function (selectedItem) {
+                    if (selectedItem) {
+                        roleViewModel.refresh();
+                    }
+                });
+            }
+
+            roleViewModel.deleteRole = function (role) {
+                let modalInstance = $uibModal.open({
+                    templateUrl: 'app/modules/administrator/roleMgmt/modal/role-del.html',
+                    controller: 'roleDelController',
+                    controllerAs: 'roleDel',
+                    resolve: {
+                        delInfo: function () {
+                            return role;
+                        }
+                    }
+                });
+                modalInstance.result.then(function (selectedItem) {
+                    if (selectedItem) {
+                        roleViewModel.refresh();
+                    }
+                });
+            }
+
+            roleViewModel.manageDeviceGroup = function (role) {
+                window.localStorage.__roleInfo__ = JSON.stringify({role_id: role.id, name: role.role_name});
+            };
+            getRoles();
+        }
+    ])
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/roleMgmt.html
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/roleMgmt.html	(revision 0)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/roleMgmt.html	(working copy)
@@ -0,0 +1,57 @@
+<div class="row">
+    <div class="col-md-12">
+        <div class="widget">
+            <div class="table-toolbar">
+                <div class="btn-group">
+                    <button class="btn btn-link" title="{{ 'Refresh' | T }}" ng-click="roleMgmt.refresh()"><i
+                        class="fa fa-refresh"></i></button>
+                    <button ng-if="role_info.user_type === 'Super Admin'" class="btn btn-link" title="{{ 'Add' | T }}"
+                            ng-click="roleMgmt.addRole()"><i
+                        class="fa fa-plus-circle"></i></button>
+                </div>
+            </div>
+            <div class="table-wrapper">
+                <table st-table="displayedCollection" st-safe-src="roleMgmt.roleList"
+                       class="table table-hover table-striped">
+                    <thead>
+                    <tr>
+                        <th class="d-num">No.</th>
+                        <th class="d-name">{{ 'Role Name' | T }}</th>
+                        <th class="d-action">{{ 'Action' | T }}</th>
+                    </tr>
+                    </thead>
+                    <tbody>
+                    <tr ng-repeat="role in displayedCollection">
+                        <td>{{ $index + 1 }}</td>
+                        <td class="d-num" title="{{'Current User'|T}}">
+                            <span class="name" ng-click="roleMgmt.getDetail(role)">{{ role.role_name }}</span>
+                        </td>
+                        <td>
+                            <button class="btn-link" title="{{ 'Edit' | T }}" ng-click="roleMgmt.editRole(role)"
+                                    ng-if="role_info.user_type === 'Super Admin'"><i class="array-edit"
+                                                                                     style="font-size: 1.25em;"></i>
+                            </button>
+                            <a ui-sref="index.admin.roleMgmt.deviceGroupMap({name:role.role_name})" class="btn-link"
+                               title="{{ 'Device Management' | T }}"
+                               ng-click="roleMgmt.manageDeviceGroup(role)">
+                                <i class="array-backup" style="font-size: 1.25em;"></i></a>
+                            <button class="btn-link" title="{{ 'Delete' | T }}"
+                                    ng-if="role_info.user_type === 'Super Admin'"
+                                    ng-click="roleMgmt.deleteRole(role)">
+                                <i class="array-delete" style="font-size: 1.25em;"></i></button>
+                        </td>
+                    </tr>
+                    </tbody>
+                    <tfoot>
+                    <tr>
+                        <td colspan="5" class="text-center">
+                            <div st-pagination="" st-items-by-page="pageSize" st-displayed-pages="5"
+                                 st-page-change="onPageChange(newPage)"></div>
+                        </td>
+                    </tr>
+                    </tfoot>
+                </table>
+            </div>
+        </div>
+    </div>
+</div>
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/roleMgmt.service.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/roleMgmt.service.js	(revision 0)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/roleMgmt/roleMgmt.service.js	(working copy)
@@ -0,0 +1,98 @@
+angular.module('cm.admin')
+    .factory('roleMgmtService', [
+            '$q',
+            '$filter',
+            '$http',
+            'apiService',
+            function ($q, $filter, $http, api) {
+                return {
+                    getRoles: getRoles,
+                    addRole: addRole,
+                    updateRole: updateRole,
+                    deleteRole: deleteRole,
+                    getRoleDeviceGroupMapping: getRoleDeviceGroupMapping,
+                    updateRoleDeviceGroupMapping: updateRoleDeviceGroupMapping,
+                    getConfigFilesByRoleId: getConfigFilesByRoleId,
+                    // getDeviceRoles: getDeviceRoles,
+                    // updateRoleDeviceMapping: updateRoleDeviceMapping
+                }
+
+                function getRoles() {
+                    return api.get('/api/cm/system/user_mgmt/Role/_get_list_data');
+                }
+
+                function addRole(data) {
+                    let post_data = {
+                        post_data: JSON.stringify(data)
+                    };
+                    let url = '/api/cm/system/user_mgmt/Role/_add';
+                    return api.post(url, post_data);
+                }
+
+                function updateRole(data) {
+                    let post_data = {
+                        post_data: JSON.stringify({
+                            id: data.id,
+                            role_name: data.role_name
+                        })
+                    };
+                    let url = '/api/cm/system/user_mgmt/Role/_update/id/' + data.id;
+                    return api.post(url, post_data);
+                }
+
+                function deleteRole(data) {
+                    let post_data = {
+                        pk: JSON.stringify({id: data.id})
+                    };
+                    let url = '/api/cm/system/user_mgmt/Role/_delete';
+                    return api.post(url, post_data);
+                }
+
+                function getRoleDeviceGroupMapping(roleInfo) {
+                    let roleId = roleInfo["role_id"];
+                    if (roleId === null) {
+                        roleId = '0';
+                    }
+                    let post_data = {
+                        "role_id": roleId
+                    }
+                    let requestData = {"action": "FilterRoleDeviceGroups", "options": JSON.stringify(post_data)};
+                    let url = "/api/cm/device_mgmt/device_group/RoleDeviceGroup/_perform";
+                    return api.post(url, requestData);
+                }
+
+                function updateRoleDeviceGroupMapping(payload) {
+                    let url = "/api/cm/device_mgmt/device_group/RoleDeviceGroup/_perform";
+                    let requestData = {"action": "UpdateRoleDeviceGroups", "options": JSON.stringify(payload)}
+                    return api.post(url, requestData);
+                }
+
+                function getConfigFilesByRoleId(roleInfo) {
+                    let roleId = roleInfo["role_id"];
+                    if (roleId === null) {
+                        roleId = '0';
+                    }
+                    let post_data = {
+                        "role_id": roleId
+                    }
+                    let requestData = {"action": "ConfigFilesByRoleId", "options": JSON.stringify(post_data)};
+                    let url = "/api/cm/configuration/config_file/ConfigFile/_perform";
+                    return api.post(url, requestData);
+                }
+
+                // function getDeviceRoles() {
+                //     return api.get('/api/cm/device_mgmt/device/RoleDevice/_get_list_data');
+                // }
+
+                // function updateRoleDeviceMapping(data) {
+                //     let post_data = {
+                //         role_id: data.role_id,
+                //         devices: data.devices
+                //     };
+                //     let requestData = {"action": "UpdateRoleDevices", "options": JSON.stringify(post_data)};
+                //     let url = "/api/cm/device_mgmt/device/RoleDevice/_perform";
+                //     return api.post(url, requestData);
+                // }
+            }
+        ]
+    )
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/modal/user.add.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/modal/user.add.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/modal/user.add.controller.js	(working copy)
@@ -11,18 +11,23 @@
         'localStorageService',
         function ($scope, $rootScope, $state, $stateParams, $uibModal, $uibModalInstance, $filter, userMgmtService, localStorageService) {
             var addViewModal = this;
-            addViewModal.roleList = [
+            addViewModal.roleId = 0;
+            addViewModal.typeOfusers = [
                 {
                     'name': 'Common Admin',
-                    'value': 0
+                    'value': 'Common Admin'
+                },
+                {
+                    'name': 'Device Admin',
+                    'value': 'Device Admin',
                 },
                 {
                     'name': 'Super Admin',
-                    'value': 1
+                    'value': 'Super Admin',
                 }
             ];
 
-            addViewModal.showProgressBar = function() {
+            addViewModal.showProgressBar = function () {
                 var modalInstance = $uibModal.open({
                     templateUrl: 'app/modules/common/templates/progress.html',
                     controller: 'showProgressCtrl',
@@ -34,6 +39,18 @@
             addViewModal.close = function () {
                 $uibModalInstance.dismiss();
             };
+
+            function getUserRoles() {
+                addViewModal.roleList = undefined;
+                userMgmtService.getUserRoles().then(function (res) {
+                    if (res && res.status === 200) {
+                        addViewModal.roleList = res.data;
+                    }
+                });
+            }
+
+            getUserRoles();
+
             addViewModal.submit = function () {
                 if (addViewModal.username === undefined || addViewModal.username === '') {
                     var errorMsg = $filter('T')("{0} can't be empty!", [$filter('T')('User Name')]);
@@ -41,7 +58,7 @@
                     return;
                 } else {
                     var name_pattern = /^[a-zA-Z_]{1}[a-zA-Z0-9_]*$/;
-                    if (!name_pattern.test(addViewModal.username)){
+                    if (!name_pattern.test(addViewModal.username)) {
                         addViewModal.errorMsg = $filter('T')("Invalid {0}!", [$filter('T')('User Name')]);
                         return;
                     } else if (addViewModal.username === 'test' || addViewModal.username === 'root') {
@@ -49,7 +66,12 @@
                         return;
                     }
                 }
-                if (addViewModal.root === undefined) {
+                if (addViewModal.userType === undefined) {
+                    var errorMsg = $filter('T')("{0} can't be empty!", [$filter('T')('Type')]);
+                    addViewModal.errorMsg = errorMsg;
+                    return;
+                }
+                if (addViewModal.userType === 'Device Admin' && (addViewModal.roleId === 0 || addViewModal.roleId === undefined)) {
                     var errorMsg = $filter('T')("{0} can't be empty!", [$filter('T')('Role')]);
                     addViewModal.errorMsg = errorMsg;
                     return;
@@ -64,7 +86,7 @@
                     addViewModal.errorMsg = errorMsg;
                     return;
                 }
-                if (addViewModal.password1 != addViewModal.password2) {
+                if (addViewModal.password1 !== addViewModal.password2) {
                     addViewModal.errorMsg = $filter('T')("The passwords you typed do not match.");
                     return;
                 }
@@ -85,11 +107,15 @@
                     return;
                 }
                 addViewModal.showProgressBar();
+                addViewModal.root = 0;
+                if (addViewModal.userType === "Super Admin") addViewModal.root = 1;
                 var data = {
-                    username : addViewModal.username.replace(/\s/g, ""),
+                    username: addViewModal.username.replace(/\s/g, ""),
+                    user_type: addViewModal.userType,
+                    role_id: addViewModal.roleId,
                     root: addViewModal.root,
-                    passwords : addViewModal.password1,
-                    level : 'config',
+                    passwords: addViewModal.password1,
+                    level: 'config',
                     email: addViewModal.email.replace(/\s/g, ""),
                     phone_num: addViewModal.phone
                 };
@@ -101,7 +127,7 @@
                             addViewModal.errorMsg = response.data[1];
                         } else {
                             if (response.data[2] && angular.isArray(response.data[2])
-                                    && response.data[2].length === 1 && response.data[2][0].length == 2) {
+                                && response.data[2].length === 1 && response.data[2][0].length === 2) {
                                 addViewModal.errorMsg = $filter("T")(response.data[2][0][1]);
                             } else {
                                 $uibModalInstance.close(true);
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/modal/user.add.html
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/modal/user.add.html	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/modal/user.add.html	(working copy)
@@ -1,7 +1,8 @@
 <div class="">
     <div class="modal-header">
         <!-- <div class="title"><i class="array-add"></i>{{ 'Add System Administrator' | T}}</div> -->
-        <button type="button" class="close" ng-click="userAdd.close()" aria-label="Close"><span aria-hidden="true">&times;</span></button>
+        <button type="button" class="close" ng-click="userAdd.close()" aria-label="Close"><span aria-hidden="true">&times;</span>
+        </button>
         <h4 class="modal-title">{{ 'Add System Administrator' | T}}</h4>
     </div>
     <div class="modal-body">
@@ -13,11 +14,19 @@
                 </div>
             </div>
             <div class="form-group">
-                <label class="control-label col-md-3">{{ 'Role' | T }}</label>
+                <label class="control-label col-md-3">{{ 'Type' | T }}</label>
                 <div class="col-md-8">
-                    <select name="role" class="form-control" ng-model="userAdd.root">
+                    <select name="type" class="form-control" ng-model="userAdd.userType">
                         <option value="">{{'--- Please Select ---' | T}}</option>
-                        <option ng-repeat="row in userAdd.roleList" value="{{row.value}}">{{row.name|T}}</option>
+                        <option ng-repeat="row in userAdd.typeOfusers" value="{{row.value}}">{{row.name|T}}</option>
+                    </select>
+                </div>
+            </div>
+            <div class="form-group" ng-if="userAdd.userType == 'Device Admin'">
+                <label class="control-label col-md-3">{{ 'Role' | T }}</label>
+                <div class="col-md-8">
+                    <select name="role" class="form-control" ng-model="userAdd.roleId">
+                        <option ng-repeat="row in userAdd.roleList" value="{{row.id}}">{{row.role_name|T}}</option>
                     </select>
                 </div>
             </div>
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/modal/user.auth.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/modal/user.auth.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/modal/user.auth.controller.js	(working copy)
@@ -20,7 +20,7 @@
             authViewModal.current_user = user_info.current_user;
             authViewModal.root = user_info.root;
             authViewModal.current_user_root = modalData.root;
-
+            authViewModal.modalData = modalData;
             authViewModal.data = {
                 "username": modalData.username,
                 "auth": modalData.auth
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/modal/user.auth.html
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/modal/user.auth.html	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/modal/user.auth.html	(working copy)
@@ -1,11 +1,19 @@
 <div class="">
     <div class="modal-header">
-        <button type="button" class="close" ng-click="userAuth.close()" aria-label="Close"><span aria-hidden="true">&times;</span></button>
+        <button type="button" class="close" ng-click="userAuth.close()" aria-label="Close"><span aria-hidden="true">&times;</span>
+        </button>
         <h4><i class="fa fa-list-ul"></i>{{ 'User Authorization' | T}}</h4>
     </div>
     <div class="modal-body">
-        <div ng-if="!userAuth.current_user_root" class="alert alert-info ng-binding" role="alert">{{'User Authorization is assigned by super admin user. User permissions are divided into two parts, one is used to control show or hide modules on sidebar, and the other is used to control permissions for specific functions. For example, if the "add", "delete" and "save configurations" of module "device" is selected but "device" is not checked, then when this user logs in, module "device" cannot be displayed on the left sidebar.'|T}}</div>
-        <div ng-if="userAuth.current_user_root" class="alert alert-info ng-binding" role="alert">{{'Super admin user has all authorization.'|T}}</div>
+        <div ng-if="!userAuth.current_user_root" class="alert alert-info ng-binding" role="alert">{{'User Authorization
+            is assigned by super admin user. User permissions are divided into two parts, one is used to control show or
+            hide modules on sidebar, and the other is used to control permissions for specific functions. For example,
+            if the "add", "delete" and "save configurations" of module "device" is selected but "device" is not checked,
+            then when this user logs in, module "device" cannot be displayed on the left sidebar.'|T}}
+        </div>
+        <div ng-if="userAuth.current_user_root" class="alert alert-info ng-binding" role="alert">{{'Super admin user has
+            all authorization.'|T}}
+        </div>
         <form name="update_auth" class="form-horizontal">
             <div class="form-group">
                 <label class="control-label col-md-3">{{ 'Username' | T }}</label>
@@ -15,7 +23,8 @@
                 <label class="control-label col-md-3" style="font-weight:bold;">{{ 'All' | T }}</label>
                 <div class="col-md-8">
                     <label class="checkbox-inline">
-                        <input type="checkbox" ng-model="userAuth.is_all_auth" ng-click="userAuth.check_all()" ng-disabled="!userAuth.root || userAuth.current_user_root">
+                        <input type="checkbox" ng-model="userAuth.is_all_auth" ng-click="userAuth.check_all()"
+                               ng-disabled="!userAuth.root || userAuth.current_user_root">
                     </label>
                 </div>
             </div>
@@ -25,12 +34,16 @@
                     <div class="col-md-12" style="padding-left: 0;">
                         <div class="col-md-3" style="padding: 0;">
                             <label class="checkbox-inline" style="margin-left: 0; margin-right: 35px; width: 100px;">
-                                <input type="checkbox" ng-model="userAuth.parsed_auth[each.name]['access']" ng-disabled="!userAuth.root || userAuth.current_user_root">
+                                <input type="checkbox" ng-model="userAuth.parsed_auth[each.name]['access']"
+                                       ng-disabled="!userAuth.root || userAuth.current_user_root">
                             </label>
                         </div>
                         <div class="col-md-9">
-                            <label ng-repeat="each_auth in each.auth" class="checkbox-inline" style="margin-left: 0; margin-right: 10px;" ng-if="each_auth.name != 'access'">
-                                <input type="checkbox" ng-model="userAuth.parsed_auth[each.name][each_auth.name]" ng-disabled="!userAuth.root || userAuth.current_user_root">{{ each_auth.verbose_name | T }}
+                            <label ng-repeat="each_auth in each.auth" class="checkbox-inline"
+                                   style="margin-left: 0; margin-right: 10px;" ng-if="each_auth.name != 'access'">
+                                <input type="checkbox" ng-model="userAuth.parsed_auth[each.name][each_auth.name]"
+                                       ng-disabled="(!userAuth.root || userAuth.current_user_root)">{{
+                                each_auth.verbose_name | T }}
                             </label>
                         </div>
                     </div>
@@ -39,29 +52,45 @@
                     <div class="col-md-12" ng-repeat="each_sub in each.sub" style="padding-left: 0;">
                         <div class="col-md-3" style="padding: 0;">
                             <label class="checkbox-inline" style="margin-left: 0; width: 100px;">
-                                <input type="checkbox" ng-model="userAuth.parsed_auth[each.name][each_sub.name]['access']" ng-disabled="!userAuth.root || userAuth.current_user_root">{{ each_sub.verbose_name | T }}
+                                <input type="checkbox"
+                                       ng-model="userAuth.parsed_auth[each.name][each_sub.name]['access']"
+                                       ng-disabled="!userAuth.root || userAuth.current_user_root || ((each_sub.verbose_name == 'Device' || each_sub.verbose_name == 'Device Group') && userAuth.modalData.user_type == 'Device Admin')">{{
+                                each_sub.verbose_name | T }}
                             </label>
                         </div>
                         <div class="col-md-9">
-                            <label ng-repeat="each_auth in each_sub.auth" class="checkbox-inline" style="margin-left: 0; margin-right: 10px;" ng-if="each_auth.name != 'access'" ng-class="{ block:  each_auth.name == 'all_rs_block'}">
-                                <input type="checkbox" ng-model="userAuth.parsed_auth[each.name][each_sub.name][each_auth.name]" ng-if="each_auth.name != 'access'" ng-disabled="!userAuth.root || userAuth.current_user_root">
+                            <label ng-repeat="each_auth in each_sub.auth" class="checkbox-inline"
+                                   style="margin-left: 0; margin-right: 10px;" ng-if="each_auth.name != 'access'"
+                                   ng-class="{ block:  each_auth.name == 'all_rs_block'}">
+                                <input type="checkbox"
+                                       ng-model="userAuth.parsed_auth[each.name][each_sub.name][each_auth.name]"
+                                       ng-if="each_auth.name != 'access'"
+                                       ng-disabled="!userAuth.root || userAuth.current_user_root || ((each_sub.verbose_name == 'Device' || each_sub.verbose_name == 'Device Group') && userAuth.modalData.user_type == 'Device Admin')">
                                 {{ each_auth.verbose_name | T }}
                                 <!-- here are special auth -->
-                                <div class="form-group" ng-if="each_auth.name == 'all_rs_block' && userAuth.parsed_auth[each.name][each_sub.name][each_auth.name] != true" style="display: flex; padding-left: 15px; margin-top: 3px;">
-                                    <label class="control-label" style="text-align: left; margin-top: 3px; margin-right: 5px;">{{ 'Available Block' | T }}</label>
+                                <div class="form-group"
+                                     ng-if="each_auth.name == 'all_rs_block' && userAuth.parsed_auth[each.name][each_sub.name][each_auth.name] != true"
+                                     style="display: flex; padding-left: 15px; margin-top: 3px;">
+                                    <label class="control-label"
+                                           style="text-align: left; margin-top: 3px; margin-right: 5px;">{{ 'Available
+                                        Block' | T }}</label>
                                     <div class="">
-                                        <select bs-select multiple class="form-control selectpick input-sm" ng-model="userAuth.parsed_auth[each.name][each_sub.name][each_auth.name]">
-                                            <option ng-repeat="block in userAuth.rs_blocks" value="{{ block }}">{{ block }}</option>
+                                        <select bs-select multiple class="form-control selectpick input-sm"
+                                                ng-model="userAuth.parsed_auth[each.name][each_sub.name][each_auth.name]">
+                                            <option ng-repeat="block in userAuth.rs_blocks" value="{{ block }}">{{ block
+                                                }}
+                                            </option>
                                         </select>
                                     </div>
-                            </div> 
+                                </div>
                             </label>
                         </div>
                     </div>
                 </div>
                 <div class="col-md-9" ng-if="!each.sub">
                     <label class="checkbox-inline">
-                        <input type="checkbox" ng-model="userAuth.parsed_auth[each.name]" ng-disabled="!userAuth.root || userAuth.current_user_root">
+                        <input type="checkbox" ng-model="userAuth.parsed_auth[each.name]"
+                               ng-disabled="!userAuth.root || userAuth.current_user_root">
                     </label>
                 </div>
             </div>
@@ -76,7 +105,7 @@
 </div>
 
 <style>
-.modal-dialog {
-    width: 700px;
-}
+    .modal-dialog {
+        width: 700px;
+    }
 </style>
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/modal/user.edit.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/modal/user.edit.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/modal/user.edit.controller.js	(working copy)
@@ -13,14 +13,32 @@
         function ($scope, $rootScope, $state, $stateParams, $uibModal, $uibModalInstance, $filter, userMgmtService, modalData, localStorageService) {
             var editViewModal = this;
 
+            editViewModal.typeOfusers = [
+                {
+                    'name': 'Common Admin',
+                    'value': 'Common Admin'
+                },
+                {
+                    'name': 'Device Admin',
+                    'value': 'Device Admin',
+                },
+                {
+                    'name': 'Super Admin',
+                    'value': 'Super Admin',
+                }
+            ];
+
             editViewModal.root = localStorageService.getWebStorage("user_info").root;
             editViewModal.username = localStorageService.getWebStorage("user_info").current_user;
             editViewModal.current_user_name = modalData.username;
 
-            var root = modalData.root ? 1:0;
+            var root = modalData.root ? 1 : 0;
+
             editViewModal.data = {
                 "username": modalData.username,
-                "root": root+'',
+                "root": root + '',
+                userType: modalData.user_type,
+                roleId: modalData.role_id,
                 //"level": modalData.level,
                 "password1": '......',//for display,not real value
                 "password2": '......',
@@ -30,7 +48,7 @@
                 "phone_num": modalData.phone_num
             };
 
-            editViewModal.showProgressBar = function() {
+            editViewModal.showProgressBar = function () {
                 var modalInstance = $uibModal.open({
                     templateUrl: 'app/modules/common/templates/progress.html',
                     controller: 'showProgressCtrl',
@@ -53,7 +71,7 @@
                     return;
                 }
                 if (editViewModal.data.realPassword1 != editViewModal.data.realPassword2) {
-                    editViewModal.errorMsg =  $filter('T')("The passwords you typed do not match.");
+                    editViewModal.errorMsg = $filter('T')("The passwords you typed do not match.");
                     return false;
                 }
 
@@ -75,11 +93,13 @@
 
                 editViewModal.showProgressBar();
                 var data = {
-                    passwords : editViewModal.data.realPassword1,
+                    passwords: editViewModal.data.realPassword1,
+                    user_type: editViewModal.data.userType,
+                    role_id: editViewModal.data.roleId,
                     root: editViewModal.data.root,
                     //level : editViewModal.data.level,
                     email: editViewModal.data.email,
-                    phone_num : editViewModal.data.phone_num
+                    phone_num: editViewModal.data.phone_num
                 };
 
                 userMgmtService.modifyUser(editViewModal.data.username, data).then(function (response) {
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/modal/user.edit.html
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/modal/user.edit.html	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/modal/user.edit.html	(working copy)
@@ -12,11 +12,16 @@
                 </div>
             </div>
             <div class="form-group">
+                <label class="control-label col-md-3">{{ 'Username' | T }}</label>
+                <div class="col-md-8">
+                    <input type="text" class="form-control" ng-model="userEdit.data.userType" readonly="true">
+                </div>
+            </div>
+            <div class="form-group" ng-if="userAdd.userType == 'Device Admin'">
                 <label class="control-label col-md-3">{{ 'Role' | T }}</label>
                 <div class="col-md-8">
-                    <select name="role" class="form-control" ng-model="userEdit.data.root" ng-disabled="!userEdit.root || userEdit.username == userEdit.current_user_name">
-                        <option value="0">{{'Common Admin'|T}}</option>
-                        <option value="1">{{'Super Admin'|T}}</option>
+                    <select name="role" class="form-control" ng-model="userEdit.data.roleId">
+                        <option ng-repeat="row in userAdd.roleList" value="{{row.id}}">{{row.role_name|T}}</option>
                     </select>
                 </div>
             </div>
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/userMgmt.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/userMgmt.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/userMgmt.controller.js	(working copy)
@@ -18,7 +18,7 @@
             var administratorViewModel = this;
             administratorViewModel.current_user = user_info.current_user;
             administratorViewModel.root = user_info.root;
-            
+
             $scope.currentPageIndex = 1;
             $scope.pageSize = 10;
             $scope.onPageChange = function (newPage) {
@@ -29,11 +29,7 @@
                 if (administratorViewModel.root) {
                     return true;
                 } else {
-                    if (administratorViewModel.current_user == user.username) {
-                        return true; 
-                    } else {
-                        return false;
-                    }
+                    return administratorViewModel.current_user === user.username;
                 }
             };
 
@@ -92,9 +88,11 @@
             };
 
             administratorViewModel.editUserInfo = function (user) {
-                var user = {
+                user = {
                     username: user.username,
                     root: user.root,
+                    user_type: user.user_type,
+                    role_id: user.role_id,
                     level :'config',
                     passwords: user.passwords,
                     email: user.email,
@@ -119,10 +117,11 @@
             };
 
             administratorViewModel.editUserAuth = function (user) {
-                var user = {
+                user = {
                     username: user.username,
                     root: user.root,
-                    auth: null
+                    auth: null,
+                    user_type: user.user_type,
                 };
                 // fetch user auth info through api
                 userMgmtService.getUserAuth(user.username).then(function (res) {
@@ -151,6 +150,10 @@
                 window.open("/configExport/system,user_mgmt,Administrator+system,user_mgmt,UserAuthorization", "Export");
             };
 
+            administratorViewModel.manageDeviceGroup = function (user) {
+                window.localStorage.__roleInfo__ = JSON.stringify({role_id: user.role_id, name: user.role_name});
+            }
+
             var fileUploader = administratorViewModel.fileUploader = new FileUploader({
                 queueLimit: 1,
                 url: '/configImport/system,user_mgmt,Administrator+system,user_mgmt,UserAuthorization',
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/userMgmt.html
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/userMgmt.html	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/userMgmt.html	(working copy)
@@ -3,20 +3,27 @@
         <div class="widget">
             <div class="table-toolbar">
                 <div class="btn-group">
-                    <button class="btn btn-link" title="{{ 'Refresh' | T }}" ng-click="userMgmt.refresh()"><i class="fa fa-refresh"></i></button>
-                    <button ng-if="userMgmt.root" class="btn btn-link" title="{{ 'Add' | T }}" ng-click="userMgmt.addUser()"><i class="fa fa-plus-circle"></i></button>
-                    <button ng-if="userMgmt.root" class="btn btn-link" title="{{ 'Export' | T }}" ng-click="userMgmt.export()"><i class="fa fa-sign-out"></i></button>
-                    <button ng-if="userMgmt.root" class="btn btn-link" title="{{ 'Import' | T }}"><i class="fa fa-sign-in"></i></button>
-                    <input title="{{ 'Import' | T }}" type="file" id="uploadfield" class="file form-control" nv-file-select uploader="userMgmt.fileUploader">
+                    <button class="btn btn-link" title="{{ 'Refresh' | T }}" ng-click="userMgmt.refresh()"><i
+                        class="fa fa-refresh"></i></button>
+                    <button ng-if="userMgmt.root" class="btn btn-link" title="{{ 'Add' | T }}"
+                            ng-click="userMgmt.addUser()"><i class="fa fa-plus-circle"></i></button>
+                    <button ng-if="userMgmt.root" class="btn btn-link" title="{{ 'Export' | T }}"
+                            ng-click="userMgmt.export()"><i class="fa fa-sign-out"></i></button>
+                    <button ng-if="userMgmt.root" class="btn btn-link" title="{{ 'Import' | T }}"><i
+                        class="fa fa-sign-in"></i></button>
+                    <input title="{{ 'Import' | T }}" type="file" id="uploadfield" class="file form-control"
+                           nv-file-select uploader="userMgmt.fileUploader">
                 </div>
             </div>
             <div class="table-wrapper">
-                <table st-table="displayedCollection" st-safe-src="userMgmt.userList" class="table table-hover table-striped">
+                <table st-table="displayedCollection" st-safe-src="userMgmt.userList"
+                       class="table table-hover table-striped">
                     <thead>
                     <tr>
                         <th class="d-num">No.</th>
                         <th class="d-name">{{ 'Username' | T }}</th>
                         <th class="d-type">{{ 'Type' | T }}</th>
+                        <th class="d-type">{{ 'Role Name' | T }}</th>
                         <th class="d-name">{{ 'Email' | T }}</th>
                         <th class="d-action">{{ 'Phone' | T }}</th>
                         <th class="d-action">{{ 'Action' | T }}</th>
@@ -24,28 +31,50 @@
                     <tr>
                         <th></th>
                         <th>
-                            <input st-search="username" placeholder="{{'Search by Username'|T}}" class="input-sm form-control" type="text" />
+                            <input st-search="username" placeholder="{{'Search by Username'|T}}"
+                                   class="input-sm form-control" type="text"/>
                         </th>
                         <th></th>
-                        <th><input st-search="email" placeholder="{{'Search by Email'|T}}" class="input-sm form-control" type="text" /></th>
-                        <th><input st-search="phone_num" placeholder="{{'Search by Phone'|T}}" class="input-sm form-control" type="text" /></th>
+                        <th><input st-search="email" placeholder="{{'Search by Email'|T}}" class="input-sm form-control"
+                                   type="text"/></th>
+                        <th><input st-search="phone_num" placeholder="{{'Search by Phone'|T}}"
+                                   class="input-sm form-control" type="text"/></th>
                         <th></th>
                     </tr>
                     </thead>
                     <tbody>
                     <tr ng-repeat="user in displayedCollection">
-                        <td style="font-weight:bold;font-style:oblique;color:red;" title="{{'Current User'|T}}" ng-if="userMgmt.current_user == user.username" class="d-num">{{ $index + 1 }}</td>
-                        <td ng-if="userMgmt.current_user != user.username" class="d-num">{{ ((currentPageIndex - 1) * pageSize) + $index + 1 }}</td>
-                        <td style="font-weight:bold;font-style:oblique;color:red;" title="{{'Current User'|T}}" ng-if="userMgmt.current_user == user.username">{{ user.username }}</td>
+                        <td style="font-weight:bold;font-style:oblique;color:red;" title="{{'Current User'|T}}"
+                            ng-if="userMgmt.current_user == user.username" class="d-num">{{ $index + 1 }}
+                        </td>
+                        <td ng-if="userMgmt.current_user != user.username" class="d-num">{{ ((currentPageIndex - 1) *
+                            pageSize) + $index + 1 }}
+                        </td>
+                        <td style="font-weight:bold;font-style:oblique;color:red;" title="{{'Current User'|T}}"
+                            ng-if="userMgmt.current_user == user.username">{{ user.username }}
+                        </td>
                         <td ng-if="userMgmt.current_user != user.username">{{ user.username }}</td>
-                        <td ng-if="user.root">{{ 'Super Admin' | T }}</td>
-                        <td ng-if="!user.root">{{ 'Common Admin' | T }}</td>
+                        <td ng-if="user.user_type && user.role_id != '0'"><span>{{ user.user_type }}</span></td>
+                        <td ng-if="user.role_id == '0' && user.root"><span>Super Admin</span></td>
+                        <td ng-if="user.role_id == '0' && !user.root"><span>Common Admin</span></td>
+                        <td><span ng-if="user.role_name">{{ user.role_name }}</span></td>
                         <td>{{ user.email }}</td>
                         <td>{{ user.phone_num }}</td>
                         <td ng-if="userMgmt.show_action_button(user)">
-                            <button class="btn-link" title="{{ 'Edit' | T }}" ng-click="userMgmt.editUserInfo(user)"><i class="array-edit"></i></button>
-                            <button class="btn-link" title="{{ 'User Authorization' | T }}" ng-click="userMgmt.editUserAuth(user)"><i class="fa fa-list-ul"></i></button>
-                            <button ng-disabled="userMgmt.current_user == user.username" class="btn-link" title="{{ 'Delete' | T }}" ng-click="userMgmt.deleteUser(user)"><i class="array-delete"></i></button>
+                            <button class="btn-link" title="{{ 'Edit' | T }}" ng-click="userMgmt.editUserInfo(user)"><i
+                                class="array-edit"></i></button>
+                            <button ui-sref="index.admin.roleMgmt.deviceGroupMap({name:user.role_name})"
+                                    class="btn-link"
+                                    title="{{ 'Device Management' | T }}"
+                                    ng-disabled="user.user_type !== 'Device Admin'"
+                                    ng-click="userMgmt.manageDeviceGroup(user)">
+                                <i class="array-backup" style="font-size: 1.25em;"></i>
+                            </button>
+                            <button class="btn-link" title="{{ 'User Authorization' | T }}"
+                                    ng-click="userMgmt.editUserAuth(user)"><i class="fa fa-list-ul"></i></button>
+                            <button ng-disabled="userMgmt.current_user == user.username" class="btn-link"
+                                    title="{{ 'Delete' | T }}" ng-click="userMgmt.deleteUser(user)"><i
+                                class="array-delete"></i></button>
                         </td>
                         <td ng-if="!userMgmt.show_action_button(user)"></td>
                     </tr>
@@ -53,7 +82,8 @@
                     <tfoot>
                     <tr>
                         <td colspan="5" class="text-center">
-                            <div st-pagination="" st-items-by-page="pageSize" st-displayed-pages="5" st-page-change="onPageChange(newPage)"></div>
+                            <div st-pagination="" st-items-by-page="pageSize" st-displayed-pages="5"
+                                 st-page-change="onPageChange(newPage)"></div>
                         </td>
                     </tr>
                     </tfoot>
@@ -64,11 +94,11 @@
 </div>
 
 <style type="text/css">
-.file {
-    position: absolute;
-    width: 35px;
-    height: 35px;
-    left: 95px;
-    opacity: 0;
-}
+    .file {
+        position: absolute;
+        width: 35px;
+        height: 35px;
+        left: 95px;
+        opacity: 0;
+    }
 </style>
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/userMgmt.service.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/userMgmt.service.js	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/administrator/userMgmt/userMgmt.service.js	(working copy)
@@ -12,11 +12,13 @@
                 deleteUser: deleteUser,
                 getUserAuth: getUserAuth,
                 getUserAuthWhileLogin: getUserAuthWhileLogin,
-                updateUserAuth: updateUserAuth
+                updateUserAuth: updateUserAuth,
+                getUserRoles: getUserRoles,
+                getUserRoleInfo: getUserRoleInfo,
             };
 
             function getUserList () {
-                api.get('/api/cm/system/user_mgmt/UserAuthorization/_get_list_data');
+                // api.get('/api/cm/system/user_mgmt/UserAuthorization/_get_list_data');
                 return api.get('/api/cm/system/user_mgmt/Administrator/_get_list_data');
             }
 
@@ -59,5 +61,19 @@
                 var url = '/api/cm/system/user_mgmt/UserAuthorization/_update/username/%22' + name +'%22';
                 return api.post(url, post_data)
             }
+
+            function getUserRoles() {
+                return api.get('/api/cm/system/user_mgmt/Role/_get_list_data');
+            }
+
+            function getUserRoleInfo(username) {
+                let post_data = {
+                    "username": username
+                }
+                let requestData = {"action": "GetRoleByUsername", "options": JSON.stringify(post_data)};
+                let url = "/api/cm/system/user_mgmt/UserAuthorization/_perform";
+                return api.post(url, requestData);
+            }
+
         }
     ]);
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/dashboard/overview/overview.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/dashboard/overview/overview.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/dashboard/overview/overview.controller.js	(working copy)
@@ -13,11 +13,17 @@
         'dashboardService',
         'storageService',
         'timeService',
-        function ($scope, $rootScope, $state, $stateParams, $uibModal, $filter, $location, $interval, $window, dashboardService, storageService, timeService) {
+        'roleMgmtService',
+        'localStorageService',
+        function ($scope, $rootScope, $state, $stateParams, $uibModal, $filter, $location, $interval, $window, dashboardService, storageService, timeService, roleMgmtService, localStorageService) {
             $rootScope.title = "Overview";
 
             var overviewModel = this;
+            $scope.role_info = localStorageService.getWebStorage('role_info');
+            $scope.isDeviceAdmin = $scope.role_info.role_id !== null && $scope.role_info.role_id !== '0';
 
+            overviewModel.deviceList = [];
+            overviewModel.agentHost = '';
             overviewModel.licenseExpireModal = function (info) {
                 var modalInstance = $uibModal.open({
                     templateUrl: 'app/modules/common/templates/licenseExpire.html',
@@ -99,18 +105,20 @@
 
             overviewModel.tab = "device"
             overviewModel.changeTab = function (tab) {
-                if (overviewModel.tab == tab) {
+                if (overviewModel.tab === tab) {
                     return
                 }
                 overviewModel.tab = tab
-                if (overviewModel.tab == "device") {
-                    getDeviceMonitoringData()
-                } else if (overviewModel.tab == "virtual_service") {
-                    getVirtualMonitoringData()
-                } else if (overviewModel.tab == "real_service") {
-                    getRealMonitoringData()
-                } else if (overviewModel.tab == "sslvpn_service") {
-                    getSSLVPNMonitoringData()
+                if (($scope.isDeviceAdmin && overviewModel.agentHost !== '') || !$scope.isDeviceAdmin) {
+                    if (overviewModel.tab === "device") {
+                        getDeviceMonitoringData()
+                    } else if (overviewModel.tab === "virtual_service") {
+                        getVirtualMonitoringData()
+                    } else if (overviewModel.tab === "real_service") {
+                        getRealMonitoringData()
+                    } else if (overviewModel.tab === "sslvpn_service") {
+                        getSSLVPNMonitoringData()
+                    }
                 }
             }
 
@@ -119,14 +127,19 @@
                 netMemUsageList: [],
                 throughputList: []
             }
-            var getDeviceMonitoringData = function () {
+            let getDeviceMonitoringData = function () {
                 overviewModel.deviceLoading = true;
-                var query = 'select TOP(last, 5) as cpu, agent_host from (select last(cpu_usage) from snmp_system group by agent_host) where time > now()-20s;' +
+                let query = 'select TOP(last, 5) as cpu, agent_host from (select last(cpu_usage) from snmp_system group by agent_host) where time > now()-20s;' +
                     'select TOP(last, 5) as net_mem, agent_host from (select last(net_mem_usage) from snmp_system group by agent_host) where time > now()-20s;' +
                     'select TOP(total, 5), received, sent, agent_host from (select last(received)+last(sent) as total, last(received) as received, last(sent) as sent from (SELECT non_negative_derivative(first(total_in), 1s)*8 as received, non_negative_derivative(first(total_out), 1s)*8 as sent FROM snmp_system WHERE time > now()-30s group by time(10s), agent_host) group by agent_host)'
+                if($scope.isDeviceAdmin) {
+                    query = 'select TOP(last, 5) as cpu, agent_host from (select last(cpu_usage) from snmp_system group by agent_host) where agent_host =~ '+ overviewModel.agentHost +' and time > now()-20s;' +
+                        'select TOP(last, 5) as net_mem, agent_host from (select last(net_mem_usage) from snmp_system group by agent_host) where agent_host =~ '+ overviewModel.agentHost +' and time > now()-20s;' +
+                        'select TOP(total, 5), received, sent, agent_host from (select last(received)+last(sent) as total, last(received) as received, last(sent) as sent from (SELECT non_negative_derivative(first(total_in), 1s)*8 as received, non_negative_derivative(first(total_out), 1s)*8 as sent FROM snmp_system WHERE agent_host =~ '+ overviewModel.agentHost +' and time > now()-30s group by time(10s), agent_host) group by agent_host)'
+                }
                 dashboardService.influxdb_proxy({ "q": query }).then(function (res) {
                     overviewModel.deviceLoading = false;
-                    if (res && res.status == 200) {
+                    if (res && res.status === 200) {
                         var cpuUsageList = []
                         if (res.data.results[0].series) {
                             _.each(res.data.results[0].series[0].values, function (value) {
@@ -181,14 +194,19 @@
                 connectionsList: [],
                 SLBThroughputList: []
             }
-            var getVirtualMonitoringData = function () {
+            let getVirtualMonitoringData = function () {
                 overviewModel.vsLoading = true;
-                var query = 'select TOP(hits, 5), ServerId, agent_host from (SELECT max(totalHits)-min(totalHits) as hits FROM virtualStats group by agent_host, ServerId) WHERE time > now()-20s;' +
+                let query = 'select TOP(hits, 5), ServerId, agent_host from (SELECT max(totalHits)-min(totalHits) as hits FROM virtualStats group by agent_host, ServerId) WHERE time > now()-20s;' +
                     'select TOP(last, 5), ServerId, agent_host from (select last(ConnCnt) from virtualStats group by ServerId, agent_host) where time > now()-20s;' +
                     'select TOP(total, 5), received, sent, ServerId, agent_host from (select last(InBytePerSec)+last(OutBytePerSec) as total, last(InBytePerSec)*8 as received, last(OutBytePerSec)*8 as sent from virtualStats group by ServerId, agent_host) where time > now()-20s;'
+                if($scope.isDeviceAdmin) {
+                    query = 'select TOP(hits, 5), ServerId, agent_host from (SELECT max(totalHits)-min(totalHits) as hits FROM virtualStats group by agent_host, ServerId) WHERE agent_host =~ '+ overviewModel.agentHost +' and time > now()-20s;' +
+                        'select TOP(last, 5), ServerId, agent_host from (select last(ConnCnt) from virtualStats group by ServerId, agent_host) where agent_host =~ '+ overviewModel.agentHost +' and time > now()-20s;' +
+                        'select TOP(total, 5), received, sent, ServerId, agent_host from (select last(InBytePerSec)+last(OutBytePerSec) as total, last(InBytePerSec)*8 as received, last(OutBytePerSec)*8 as sent from virtualStats group by ServerId, agent_host) where agent_host =~ '+ overviewModel.agentHost +' and time > now()-20s;'
+                }
                 dashboardService.influxdb_proxy({ "q": query }).then(function (res) {
                     overviewModel.vsLoading = false;
-                    if (res && res.status == 200) {
+                    if (res && res.status === 200) {
                         var hitsList = []
                         if (res.data.results[0].series) {
                             _.each(res.data.results[0].series[0].values, function (value) {
@@ -234,14 +252,19 @@
                 rsConnPerSecList: [],
                 throughputList: []
             }
-            var getRealMonitoringData = function () {
+            let getRealMonitoringData = function () {
                 overviewModel.rsLoading = true;
-                var query = 'select TOP(last, 5), realServerId, agent_host from (select last(rsCntOfReq) from realStats group by realServerId, agent_host) where time > now()-20s;' +
+                let query = 'select TOP(last, 5), realServerId, agent_host from (select last(rsCntOfReq) from realStats group by realServerId, agent_host) where time > now()-20s;' +
                     'select TOP(last, 5), realServerId, agent_host from (select last(rsConnPerSec) from realStats group by realServerId, agent_host) where time > now()-20s;' +
                     'select TOP(total, 5), received, sent, realServerId, agent_host from (select last(rsInBytePerSec)+last(rsOutBytePerSec) as total, last(rsInBytePerSec)*8 as received, last(rsOutBytePerSec)*8 as sent from realStats group by realServerId, agent_host) where time > now()-20s;'
+                if ($scope.isDeviceAdmin) {
+                    query = 'select TOP(last, 5), realServerId, agent_host from (select last(rsCntOfReq) from realStats group by realServerId, agent_host) where agent_host =~ '+ overviewModel.agentHost +' and time > now()-20s;' +
+                        'select TOP(last, 5), realServerId, agent_host from (select last(rsConnPerSec) from realStats group by realServerId, agent_host) where agent_host =~ '+ overviewModel.agentHost +' and time > now()-20s;' +
+                        'select TOP(total, 5), received, sent, realServerId, agent_host from (select last(rsInBytePerSec)+last(rsOutBytePerSec) as total, last(rsInBytePerSec)*8 as received, last(rsOutBytePerSec)*8 as sent from realStats group by realServerId, agent_host) where agent_host =~ '+ overviewModel.agentHost +' and time > now()-20s;'
+                }
                 dashboardService.influxdb_proxy({ "q": query }).then(function (res) {
                     overviewModel.rsLoading = false;
-                    if (res && res.status == 200) {
+                    if (res && res.status === 200) {
                         var rsCntOfReqList = []
                         if (res.data.results[0].series) {
                             _.each(res.data.results[0].series[0].values, function (value) {
@@ -287,14 +310,19 @@
                 clientThroughputList: [],
                 ServerThroughputList: []
             }
-            var getSSLVPNMonitoringData = function () {
+            let getSSLVPNMonitoringData = function () {
                 overviewModel.sslvpnLoading = true;
-                var query = 'select TOP(last, 5), Id, agent_host from (select last(ActiveSessions) from virtualSiteStats group by Id, agent_host) where time > now()-20s;' +
+                let query = 'select TOP(last, 5), Id, agent_host from (select last(ActiveSessions) from virtualSiteStats group by Id, agent_host) where time > now()-20s;' +
                     'select TOP(total, 5), received, sent, Id, agent_host from (select last(received)+last(sent) as total, last(received) as received, last(sent) as sent from (SELECT non_negative_derivative(first(ClientBytesIn), 1s)*8 as received, non_negative_derivative(first(ClientBytesOut), 1s)*8 as sent FROM virtualSiteStats WHERE time > now()-30s group by time(10s), Id, agent_host) group by Id, agent_host);' +
                     'select TOP(total, 5), received, sent, Id, agent_host from (select last(received)+last(sent) as total, last(received) as received, last(sent) as sent from (SELECT non_negative_derivative(first(ServerBytesIn), 1s)*8 as received, non_negative_derivative(first(ServerBytesOut), 1s)*8 as sent FROM virtualSiteStats WHERE time > now()-30s group by time(10s), Id, agent_host) group by Id, agent_host);'
+                if ($scope.isDeviceAdmin) {
+                    query = 'select TOP(last, 5), Id, agent_host from (select last(ActiveSessions) from virtualSiteStats group by Id, agent_host) where agent_host =~ '+ overviewModel.agentHost +' and time > now()-20s;' +
+                        'select TOP(total, 5), received, sent, Id, agent_host from (select last(received)+last(sent) as total, last(received) as received, last(sent) as sent from (SELECT non_negative_derivative(first(ClientBytesIn), 1s)*8 as received, non_negative_derivative(first(ClientBytesOut), 1s)*8 as sent FROM virtualSiteStats WHERE agent_host =~ '+ overviewModel.agentHost +' and time > now()-30s group by time(10s), Id, agent_host) group by Id, agent_host);' +
+                        'select TOP(total, 5), received, sent, Id, agent_host from (select last(received)+last(sent) as total, last(received) as received, last(sent) as sent from (SELECT non_negative_derivative(first(ServerBytesIn), 1s)*8 as received, non_negative_derivative(first(ServerBytesOut), 1s)*8 as sent FROM virtualSiteStats WHERE agent_host =~ '+ overviewModel.agentHost +' and time > now()-30s group by time(10s), Id, agent_host) group by Id, agent_host);'
+                }
                 dashboardService.influxdb_proxy({ "q": query }).then(function (res) {
                     overviewModel.sslvpnLoading = false;
-                    if (res && res.status == 200) {
+                    if (res && res.status === 200) {
                         var sessionList = []
                         if (res.data.results[0].series) {
                             _.each(res.data.results[0].series[0].values, function (value) {
@@ -338,10 +366,14 @@
 
             overviewModel.auditRange = "1h";
             overviewModel.getAuditingData = function () {
+                let remoteIPs = [];
+                overviewModel.deviceList.forEach(function (device) {
+                    remoteIPs.push( device.ip)
+                });
                 var duration = timeService.parseDuration(overviewModel.auditRange);
                 var endstamp = (new Date()).getTime()
                 if (auditingService) {
-                    var post_data = {
+                    let post_data = {
                         "from": (endstamp - duration) + '',
                         "to": endstamp + '',
                         "queries": [{
@@ -374,7 +406,7 @@
                     });
 
 
-                    var post_data = {
+                    post_data = {
                         "size": 50,
                         "sort": [
                             {
@@ -389,6 +421,7 @@
                         },
                         "query": {
                             "bool": {
+                                "must": [{"terms": {"tag.remote_ip": remoteIPs}}],
                                 "filter": [
                                     {
                                         "range": {
@@ -429,7 +462,7 @@
                                 // var points = []
                                 // _.each(res["data"]["aggregations"]["2"]["buckets"], function (bucket) {
                                 //     points.push([bucket.key, bucket.doc_count])
-                                // })                                
+                                // })
                                 // if (points.length > 0) {
                                 //     newSeries.push({
                                 //         name: $filter('T')("Log Count"),
@@ -450,21 +483,34 @@
             overviewModel.eventNum = 0;
             overviewModel.refresh = function () {
                 if (monitoringService) {
+                    overviewModel.agentHost = '';
+                    overviewModel.deviceList = [];
+                    // fetch the device group information for the specific role.
                     monitoringService.getDeviceList().then(function (res) {
                         overviewModel.deviceMap = {}
+                        overviewModel.deviceList = res;
                         _.each(res, function (host) {
                             overviewModel.deviceMap[host.ip] = host;
+                            if (overviewModel.agentHost === '') {
+                                overviewModel.agentHost = overviewModel.agentHost + '/' + host.ip;
+                            } else {
+                                overviewModel.agentHost = overviewModel.agentHost + '|' + host.ip;
+                            }
                         });
-                        if (overviewModel.tab == "device") {
-                            getDeviceMonitoringData()
-                        } else if (overviewModel.tab == "virtual_service") {
-                            getVirtualMonitoringData()
-                        } else if (overviewModel.tab == "real_service") {
-                            getRealMonitoringData()
-                        } else if (overviewModel.tab == "sslvpn_service") {
-                            getSSLVPNMonitoringData()
+                        if (overviewModel.agentHost !== '') overviewModel.agentHost += '/';
+                        if (($scope.isDeviceAdmin && overviewModel.agentHost !== '') || !$scope.isDeviceAdmin) {
+                            if (overviewModel.tab === "device") {
+                                getDeviceMonitoringData()
+                            } else if (overviewModel.tab === "virtual_service") {
+                                getVirtualMonitoringData()
+                            } else if (overviewModel.tab === "real_service") {
+                                getRealMonitoringData()
+                            } else if (overviewModel.tab === "sslvpn_service") {
+                                getSSLVPNMonitoringData()
+                            }
                         }
-                    });
+                        overviewModel.getAuditingData();
+                    })
                 }
 
                 if (alertService) {
@@ -520,63 +566,8 @@
                         overviewModel.eventNum = eventNum;
                     }
                 });
-
-                // if (reportingService) {
-                //     reportingService.get_report_list().then(function (resp) {
-                //         if (resp && resp.status === 200) {
-                //             if (resp.data.code == 0) {
-                //                 var running = 0;
-                //                 var not_running = 0;
-                //                 var ready = 0;
-                //                 _.each(resp.data.data.data, function (each_data) {
-                //                     if (each_data.status == 1) {
-                //                         running++
-                //                     } else if (each_data.status == 0) {
-                //                         not_running++
-                //                     } else {
-                //                         ready++
-                //                     }
-                //                 })
-                //                 overviewModel.reportingWidget.seriesData = [{
-                //                     name: $filter('T')('Not Running'),
-                //                     value: not_running
-                //                 }, {
-                //                     name: $filter('T')('Running'),
-                //                     value: running
-                //                 }, {
-                //                     name: $filter('T')('Ready'),
-                //                     value: ready
-                //                 }]
-                //             }
-                //         }
-                //     });
-
-                //     var start = 0;     //从第几条数据开始查询，默认0条
-                //     var number = 4;   //每页显示条数
-                //     var page = start / number + 1
-                //     var url = "?page=" + page + "&page_size=" + number;
-                //     url += "&status=3"
-
-                //     reportingService.getReportLogList(url).then(function (res) {
-                //         if (res.status === 200) {
-                //             if (res.data.code === 0) {
-                //                 var dataList = res.data.data.data;
-                //                 dataList.forEach(function (item) {
-                //                     var date = new Date(item.start_time);
-                //                     item.time_text = date.format('yyyy-mm-dd HH:MM:ss');
-                //                     item.subject_type = item.tags[0]
-                //                     item.subject_name = item.tags[1]
-                //                     // item.file_size = JSON.parse(item.result)['size']
-                //                 })
-                //                 overviewModel.reportList = dataList;
-                //             }
-                //         }
-                //     })
-                // }
-
             }
             overviewModel.refresh();
-            overviewModel.getAuditingData();
 
             if (!angular.isDefined($scope.DataTimer)) {
                 $scope.DataTimer = $interval(function () {
@@ -584,11 +575,11 @@
                 }, 10000);
             }
 
-            if (!angular.isDefined($scope.DataTimer2)) {
-                $scope.DataTimer2 = $interval(function () {
-                    overviewModel.getAuditingData();
-                }, 30000);
-            }
+            // if (!angular.isDefined($scope.DataTimer2)) {
+            //     $scope.DataTimer2 = $interval(function () {
+            //         overviewModel.getAuditingData();
+            //     }, 30000);
+            // }
 
             $scope.$on('$destroy', function () {
                 if (angular.isDefined($scope.DataTimer)) {
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/dashboard/system_statistics/system_statistics.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/dashboard/system_statistics/system_statistics.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/dashboard/system_statistics/system_statistics.controller.js	(working copy)
@@ -15,12 +15,14 @@
         'storageService',
         '$stateParams',
         '$uibModal',
-        function ($scope, $q, $rootScope, $location, $filter, $state, $interval, dashboardService, deviceService, localStorageService, taskService, storageService, $stateParams, $uibModal) {
+        'roleMgmtService',
+        function ($scope, $q, $rootScope, $location, $filter, $state, $interval, dashboardService, deviceService, localStorageService, taskService, storageService, $stateParams, $uibModal, roleMgmtService) {
             $rootScope.title = "Dashboard";
             $scope.allow_config = $rootScope.allow_config;
-
-            var dashboard = this;
-
+            $scope.role_info = localStorageService.getWebStorage('role_info');
+            $scope.isDeviceAdmin = $scope.role_info.role_id !== null && $scope.role_info.role_id !== '0';
+            let dashboard = this;
+            dashboard.agentHost = '';
             dashboard.deviceNum = 'N/A';
             dashboard.serviceNum = 'N/A';
             dashboard.taskNum = 'N/A';
@@ -105,8 +107,8 @@
                 seriesData: [0]
             }
 
-            var getSystemStatusData = function () {
-                var post_data = {
+            let getSystemStatusData = function () {
+                let post_data = {
                     "from": "now-20s",
                     "to": "now",
                     "queries": [{
@@ -128,7 +130,7 @@
                     }
                 });
 
-                var post_data = {
+                post_data = {
                     "from": "now-20s",
                     "to": "now-10s",
                     "queries": [{
@@ -164,8 +166,8 @@
             dashboard.readRate = 'N/A';
             dashboard.writeRate = 'N/A';
 
-            var getDiskStatusData = function () {
-                var post_data = {
+            let getDiskStatusData = function () {
+                let post_data = {
                     "from": "now-20s",
                     "to": "now-10s",
                     "queries": [{
@@ -181,9 +183,15 @@
                         var seriesData = [];
                         _.each(res.data.data.results['A'].series, function (series) {
                             if (series.name == "mean") {
-                                seriesData.push({ name: dashboard.diskStatusWidget.legendData[0], value: series.points[0][1] })
+                                seriesData.push({
+                                    name: dashboard.diskStatusWidget.legendData[0],
+                                    value: series.points[0][1]
+                                })
                             } else if (series.name == "mean_1") {
-                                seriesData.push({ name: dashboard.diskStatusWidget.legendData[1], value: series.points[0][1] })
+                                seriesData.push({
+                                    name: dashboard.diskStatusWidget.legendData[1],
+                                    value: series.points[0][1]
+                                })
                             } else if (series.name == "sum") {
                                 dashboard.readRate = storageService.formatBigData(series.points[0][1])
                             } else if (series.name == "sum_1") {
@@ -199,10 +207,10 @@
                 title: $filter('T')('Tasks'),
                 type: 'task',
                 legendData: [$filter('T')('Waiting'), $filter('T')('Done'), $filter('T')('Ongoing'), $filter('T')('Failed')],
-                seriesData: [{ name: $filter('T')('Waiting'), value: 0 },
-                { name: $filter('T')('Done'), value: 0 },
-                { name: $filter('T')('Ongoing'), value: 0 },
-                { name: $filter('T')('Failed'), value: 0 }]
+                seriesData: [{name: $filter('T')('Waiting'), value: 0},
+                    {name: $filter('T')('Done'), value: 0},
+                    {name: $filter('T')('Ongoing'), value: 0},
+                    {name: $filter('T')('Failed'), value: 0}]
             }
 
             var filter = function (arr, status) {
@@ -231,19 +239,20 @@
             dashboard.Inbound = 'N/A'
             dashboard.Outbound = 'N/A'
 
-            var getSystemThroughputData = function () {
-                var post_data = {
+            let getSystemThroughputData = function () {
+                let query = "SELECT (bytes_recv)*8/10, (bytes_sent)*8/10 FROM net_throughput WHERE $timeFilter AND interface = 'all'"
+                let post_data = {
                     "from": "now-30s",
                     "to": "now-10s",
                     "queries": [{
                         "datasourceId": 1,
-                        "query": "SELECT (bytes_recv)*8/10, (bytes_sent)*8/10 FROM net_throughput WHERE $timeFilter AND interface = 'all'",
+                        "query": query,
                         "rawQuery": true,
                         "resultFormat": "time_series"
                     }]
                 };
                 dashboardService.get_composer_data('/composer/tsdb/query', JSON.stringify(post_data)).then(function (res) {
-                    if (res && res.data.code == 0) {
+                    if (res && res.data.code === 0) {
                         _.each(res.data.data.results['A'].series, function (series) {
                             if (series.name == "bytes_recv") {
                                 dashboard.Inbound = storageService.formatBigData(series.points[0][1]);
@@ -305,96 +314,120 @@
 
                 if (dashboard.get_loading()) {
                     dashboard.serviceList = [];
-
-                    deviceService.getDeviceList().then(function (res) {
+                    let device_list = [];
+                    roleMgmtService.getRoleDeviceGroupMapping($scope.role_info).then(function (res) {
                         dashboard.deviceNum = 0;
+                        dashboard.agentHost = '';
                         if (res && res.status === 200 && res.data instanceof Array) {
-                            var deviceMap = {};
-                            var deviceRunMap = {};
-                            var deviceStopMap = {};
-                            var total = 0;
-                            _.each(device_type_info.DEVICE_STD_LIST, function (item) {
-                                deviceRunMap[item] = 0
-                                deviceStopMap[item] = 0
-                            })
-
-                            var CalService = function () {
-                                if (dashboard.get_loading()) {
-                                    dashboard.serviceNum = 0;
-                                    var serviceMap = {
-                                        "SLB": 0,
-                                        "SSLVPN": 0
-                                    };
-                                    _.each(dashboard.serviceList, function (service) {
-                                        dashboard.serviceNum++
-                                        if (service.origin_type == "SLB_vs") {
-                                            serviceMap["SLB"]++
-                                        } else if (service.origin_type == "SSLVPN") {
-                                            serviceMap["SSLVPN"]++
-                                        }
+                            let data = res.data;
+                            if (data.length > 1) {
+                                try {
+                                    let deviceGMap = data[1]['result'];
+                                    deviceGMap.forEach(function (deviceGroup) {
+                                        deviceGroup['device_list'].forEach(function (device) {
+                                            device_list.push(device);
+                                            if (dashboard.agentHost === '') {
+                                                dashboard.agentHost = dashboard.agentHost + '/' + device.ip;
+                                            } else {
+                                                dashboard.agentHost = dashboard.agentHost + '|' + device.ip;
+                                            }
+                                        })
                                     })
-                                    dashboard.DeviceWidget.serviceMap = serviceMap;
-                                }
-                            }
+                                    if (dashboard.agentHost !== '') dashboard.agentHost += '/';
+                                    var deviceMap = {};
+                                    var deviceRunMap = {};
+                                    var deviceStopMap = {};
+                                    var total = 0;
+                                    _.each(device_type_info.DEVICE_STD_LIST, function (item) {
+                                        deviceRunMap[item] = 0
+                                        deviceStopMap[item] = 0
+                                    })
+
+                                    var CalService = function () {
+                                        if (dashboard.get_loading()) {
+                                            dashboard.serviceNum = 0;
+                                            var serviceMap = {
+                                                "SLB": 0,
+                                                "SSLVPN": 0
+                                            };
+                                            _.each(dashboard.serviceList, function (service) {
+                                                dashboard.serviceNum++
+                                                if (service.origin_type == "SLB_vs") {
+                                                    serviceMap["SLB"]++
+                                                } else if (service.origin_type == "SSLVPN") {
+                                                    serviceMap["SSLVPN"]++
+                                                }
+                                            })
+                                            dashboard.DeviceWidget.serviceMap = serviceMap;
+                                        }
+                                    }
 
-                            _.each(res.data, function (host) {
-                                dashboard.deviceNum++
-                                if (host.connection) {
-                                    if (device_type_info.ADC_TYPE_LIST.indexOf(host.type.toLowerCase()) != -1) {
-                                        dashboard.all_loadings[host.name] = false;
-                                        dashboardService.getAllVirtualService(host.name).then(function (res) {
-                                            dashboard.all_loadings[host.name] = true;
-                                            if (res && res.status === 200 && res.data.VirtualService) {
-                                                _.each(res.data.VirtualService, function (data) {
-                                                    // if (data.protocol != 'vlink') {
-                                                    var tmp = {
-                                                        "name": data.service_name,
-                                                        "origin_type": "SLB_vs",
-                                                        "service_type": data.protocol
+                                    _.each(device_list, function (host) {
+                                        dashboard.deviceNum++
+                                        if (host.connection) {
+                                            if (device_type_info.ADC_TYPE_LIST.indexOf(host.type.toLowerCase()) !== -1) {
+                                                dashboard.all_loadings[host.name] = false;
+                                                dashboardService.getAllVirtualService(host.name).then(function (res) {
+                                                    dashboard.all_loadings[host.name] = true;
+                                                    if (res && res.status === 200 && res.data.VirtualService) {
+                                                        _.each(res.data.VirtualService, function (data) {
+                                                            // if (data.protocol != 'vlink') {
+                                                            var tmp = {
+                                                                "name": data.service_name,
+                                                                "origin_type": "SLB_vs",
+                                                                "service_type": data.protocol
+                                                            }
+                                                            dashboard.serviceList.push(tmp)
+                                                            // }
+                                                        });
                                                     }
-                                                    dashboard.serviceList.push(tmp)
-                                                    // }
+                                                    CalService()
                                                 });
-                                            }
-                                            CalService()
-                                        });
-                                    } else if (device_type_info.VPN_TYPE_LIST.indexOf(host.type.toLowerCase()) != -1) {
-                                        dashboard.all_loadings[host.name] = false;
-                                        dashboardService.getAllVirtualSite(host.name).then(function (res) {
-                                            dashboard.all_loadings[host.name] = true;
-                                            if (res && res.status === 200 && res.data.contents) {
-                                                _.each(res.data.contents, function (data) {
-                                                    var tmp = {
-                                                        "name": data.vsite_name,
-                                                        "origin_type": "SSLVPN",
-                                                        "service_type": data.vsite_type,
+                                            } else if (device_type_info.VPN_TYPE_LIST.indexOf(host.type.toLowerCase()) !== -1) {
+                                                dashboard.all_loadings[host.name] = false;
+                                                dashboardService.getAllVirtualSite(host.name).then(function (res) {
+                                                    dashboard.all_loadings[host.name] = true;
+                                                    if (res && res.status === 200 && res.data.contents) {
+                                                        _.each(res.data.contents, function (data) {
+                                                            var tmp = {
+                                                                "name": data.vsite_name,
+                                                                "origin_type": "SSLVPN",
+                                                                "service_type": data.vsite_type,
+                                                            }
+                                                            dashboard.serviceList.push(tmp)
+                                                        });
                                                     }
-                                                    dashboard.serviceList.push(tmp)
+                                                    CalService()
                                                 });
                                             }
-                                            CalService()
-                                        });
+                                            deviceRunMap[host.type]++
+                                        } else {
+                                            deviceStopMap[host.type]++
+                                        }
+                                        if (deviceMap[host.type]) {
+                                            deviceMap[host.type]++
+                                        } else {
+                                            deviceMap[host.type] = 1
+                                        }
+                                        total++
+                                    });
+
+                                    dashboard.DeviceWidget.statusMap = {
+                                        all: total,
+                                        running: deviceRunMap,
+                                        not_running: deviceStopMap
+                                    };
+                                    dashboard.DeviceWidget.deviceMap = deviceMap;
+                                    if (($scope.isDeviceAdmin && dashboard.agentHost !== '') || !$scope.isDeviceAdmin) {
+                                        getSystemThroughputData();
                                     }
-                                    deviceRunMap[host.type]++
-                                } else {
-                                    deviceStopMap[host.type]++
+                                } catch (e) {
+                                    console.log('500 - Internal server error.');
+                                    alert('500 - Internal server error. Failed to fetch device group mapping info.');
                                 }
-                                if (deviceMap[host.type]) {
-                                    deviceMap[host.type]++
-                                } else {
-                                    deviceMap[host.type] = 1
-                                }
-                                total++
-                            });
-
-                            dashboard.DeviceWidget.statusMap = {
-                                all: total,
-                                running: deviceRunMap,
-                                not_running: deviceStopMap
-                            };
-                            dashboard.DeviceWidget.deviceMap = deviceMap;
+                            }
                         }
-                        if (dashboard.deviceNum == 0) {
+                        if (dashboard.deviceNum === 0) {
                             dashboard.serviceNum = 0;
                         }
                     });
@@ -403,15 +436,12 @@
 
             getSystemStatusData();
             getDiskStatusData();
-            getSystemThroughputData();
             getTaskInfo();
             getNubData();
-
             if (!angular.isDefined($scope.DataTimer)) {
                 $scope.DataTimer = $interval(function () {
                     getSystemStatusData();
                     getDiskStatusData();
-                    getSystemThroughputData();
                     getTaskInfo();
                     getNubData();
                 }, 10000);
@@ -427,8 +457,7 @@
     ])
     .directive('diskUsage', ['$filter', '$state', '$interval', 'storageService', function ($filter, $state, $interval, storageService) {
         return {
-            scope: {
-            },
+            scope: {},
             restrict: 'A',
             replace: true,
             link: function ($scope, element, attrs, controller) {
@@ -495,6 +524,7 @@
                         default:
                             break;
                     }
+
                     function go(url) {
                         $state.go(url);
                     };
@@ -535,8 +565,7 @@
     }])
     .directive('statisticSimplePie', ['$filter', '$state', '$interval', function ($filter, $state, $interval) {
         return {
-            scope: {
-            },
+            scope: {},
             restrict: 'A',
             replace: true,
             link: function ($scope, element, attrs, controller) {
@@ -580,12 +609,10 @@
                             radius: '50%',
                             center: ['50%', '45%'],
                             label: {
-                                textStyle: {
-                                }
+                                textStyle: {}
                             },
                             labelLine: {
-                                lineStyle: {
-                                },
+                                lineStyle: {},
                                 smooth: 0.2,
                                 length: 25,
                                 length2: 15
@@ -620,6 +647,7 @@
                         default:
                             break;
                     }
+
                     function go(url) {
                         $state.go(url);
                     };
@@ -645,8 +673,7 @@
     }])
     .directive('liquidGraph', ['$filter', '$uibModal', '$state', function ($filter, $uibModal, $state) {
         return {
-            scope: {
-            },
+            scope: {},
             restrict: 'A',
             replace: true,
             link: function ($scope, element, attrs, controller) {
@@ -740,8 +767,7 @@
     }])
     .directive('deviceMonitoring', ['$filter', '$uibModal', '$state', function ($filter, $uibModal, $state) {
         return {
-            scope: {
-            },
+            scope: {},
             restrict: 'A',
             replace: true,
             link: function ($scope, element, attrs, controller) {
@@ -850,62 +876,63 @@
                         // yAxisIndex: 1,
                         // z: 3,
                     },
-                    // {
-                    //     type: 'bar',
-                    //     stack: 'component',
-                    //     silent: true,
-                    //     // xAxisIndex: 1,
-                    //     // yAxisIndex: 1,
-                    //     itemStyle: {
-                    //         normal: {
-                    //             color: 'transparent'
-                    //         }
-                    //     }
-                    // },
-                    {
-                        name: $filter('T')('Running'),
-                        type: 'bar',
-                        stack: "total",
-                    },
-                    // {
-                    //     type: 'bar',
-                    //     stack: 'chart',
-                    //     silent: true,
-                    //     itemStyle: {
-                    //         normal: {
-                    //             color: 'transparent'
-                    //         }
-                    //     }
-                    // },
-                    {
-                        type: 'pie',
-                        radius: [0, '30%'],
-                        center: ['75%', '25%'],
-                        itemStyle: {
-                            shadowColor: 'rgba(0, 0, 0, 0.5)',
-                            shadowBlur: 5
-                        },
-                        animationType: 'scale',
-                        animationEasing: 'elasticOut',
-                        animationDelay: function (idx) {
-                            return Math.random() * 200;
-                        }
-                    }, {
-                        type: 'pie',
-                        radius: [0, '30%'],
-                        center: ['75%', '75%'],
-                        itemStyle: {
-                            shadowColor: 'rgba(0, 0, 0, 0.5)',
-                            shadowBlur: 5
+                        // {
+                        //     type: 'bar',
+                        //     stack: 'component',
+                        //     silent: true,
+                        //     // xAxisIndex: 1,
+                        //     // yAxisIndex: 1,
+                        //     itemStyle: {
+                        //         normal: {
+                        //             color: 'transparent'
+                        //         }
+                        //     }
+                        // },
+                        {
+                            name: $filter('T')('Running'),
+                            type: 'bar',
+                            stack: "total",
                         },
-                        animationType: 'scale',
-                        animationEasing: 'elasticOut',
-                        animationDelay: function (idx) {
-                            return Math.random() * 200;
-                        }
-                    }]
+                        // {
+                        //     type: 'bar',
+                        //     stack: 'chart',
+                        //     silent: true,
+                        //     itemStyle: {
+                        //         normal: {
+                        //             color: 'transparent'
+                        //         }
+                        //     }
+                        // },
+                        {
+                            type: 'pie',
+                            radius: [0, '30%'],
+                            center: ['75%', '25%'],
+                            itemStyle: {
+                                shadowColor: 'rgba(0, 0, 0, 0.5)',
+                                shadowBlur: 5
+                            },
+                            animationType: 'scale',
+                            animationEasing: 'elasticOut',
+                            animationDelay: function (idx) {
+                                return Math.random() * 200;
+                            }
+                        }, {
+                            type: 'pie',
+                            radius: [0, '30%'],
+                            center: ['75%', '75%'],
+                            itemStyle: {
+                                shadowColor: 'rgba(0, 0, 0, 0.5)',
+                                shadowBlur: 5
+                            },
+                            animationType: 'scale',
+                            animationEasing: 'elasticOut',
+                            animationDelay: function (idx) {
+                                return Math.random() * 200;
+                            }
+                        }]
                 }
-                var cur_theme = window.localStorage.theme || 'dark';;
+                var cur_theme = window.localStorage.theme || 'dark';
+
                 if (cur_theme != 'dark') {
                     option.title[0].textStyle.color = '#555';
                     option.title[1].textStyle.color = '#555';
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/device/device.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/device/device.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/device/device.controller.js	(working copy)
@@ -12,11 +12,14 @@
         '$filter',
         '$interval',
         'userAuthService',
-        function ($scope, $rootScope, $state, $stateParams, $location, $uibModal, $aside, deviceService, dashboardService, $filter, $interval, userAuthService) {
+        'roleMgmtService',
+        'localStorageService',
+        function ($scope, $rootScope, $state, $stateParams, $location, $uibModal, $aside, deviceService, dashboardService, $filter, $interval, userAuthService, roleMgmtService, localStorageService) {
             $rootScope.title = 'Device';
             //get user auth data
-            //here not use localStorageService, beacuse we want to get raw str
+            //here not use localStorageService, because we want to get raw str
             $scope.user_auth_data = userAuthService.build_auth_data(0, localStorage["auth_data"]);
+            $scope.role_info = localStorageService.getWebStorage('role_info');
 
             $scope.currentPageIndex = 1;
             $scope.pageSize = 10;
@@ -39,25 +42,35 @@
                 return "REST API"
             }
 
-            // $scope.$on("$destroy", function() {
-            //     clearInterval(deviceViewModel.timer);
-            // });
-
-            // deviceViewModel.timer = setInterval(function(){
-            //     getDevice();
-            // }, 10000);
+            getRoleDeviceGroupMapping();
 
+            function getRoleDeviceGroupMapping() {
+                deviceViewModel.deviceList = [];
 
-            getDevice();
-            function getDevice() {
-                deviceService.getDeviceList().then(function (res) {
+                // fetch the device group information for the specific role.
+                roleMgmtService.getRoleDeviceGroupMapping($scope.role_info).then(function (res) {
                     if (res && res.status === 200) {
-                        var deviceList = res.data;
-                        deviceList.forEach(function (item) {
-                            item.protocol_verbose = getProtocolVerbose(item.protocol)
-                            item.webui = 'https://' + item.ip + ':' + item.webui_port;
-                        })
-                        deviceViewModel.deviceList = deviceList;
+                        try {
+                            let data = res.data;
+                            if (data.length > 1) {
+                                try {
+                                    let deviceMap = data[1]['result'];
+                                    deviceMap.forEach(function (deviceGroup) {
+                                        deviceGroup['device_list'].forEach(function (device) {
+                                            device.protocol_verbose = getProtocolVerbose(device.protocol)
+                                            device.webui = 'https://' + device.ip + ':' + device.webui_port;
+                                            deviceViewModel.deviceList.push(device);
+                                        })
+                                    })
+                                } catch (e) {
+                                    console.error('Error getRoleDeviceGroupMapping returned error.' + e);
+                                    deviceViewModel.deviceList = [];
+                                }
+                            }
+                        } catch (e) {
+                            console.log('500 - Internal server error.');
+                            alert('500 - Internal server error. Failed to fetch device group mapping info.');
+                        }
                     }
                 });
             }
@@ -74,14 +87,14 @@
                 });
                 modalInstance.result.then(function (selectedItem) {
                     if (selectedItem) {
-                        getDevice();
+                        deviceViewModel.refresh();
                     }
                 });
             };
 
             deviceViewModel.refresh = function () {
                 deviceViewModel.deviceList = undefined;
-                getDevice();
+                getRoleDeviceGroupMapping();
             };
 
             deviceViewModel.getDetail = function (deviceItem) {
@@ -112,7 +125,7 @@
                 });
                 modalInstance.result.then(function (selectedItem) {
                     if (selectedItem) {
-                        getDevice();
+                        deviceViewModel.refresh();
                     }
                 });
             };
@@ -134,7 +147,7 @@
             };
 
             deviceViewModel.licenseInfo = function (deviceItem) {
-                var licenseKey = {
+                $rootScope.__licenseKey__ = {
                     id: deviceItem.id,
                     name: deviceItem.name,
                     type: deviceItem.type,
@@ -142,7 +155,6 @@
                     license_date: deviceItem.license_date,
                     license_feature: deviceItem.license_feature
                 };
-                $rootScope.__licenseKey__ = licenseKey;
 
                 var modalInstance = $uibModal.open({
                     templateUrl: 'app/modules/device/modal/device.license.html',
@@ -154,7 +166,7 @@
                 });
                 modalInstance.result.then(function (selectedItem) {
                     if (selectedItem) {
-                        getDevice();
+                        deviceViewModel.refresh();
                     }
                 });
             }
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/device/device.html
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/device/device.html	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/device/device.html	(working copy)
@@ -9,7 +9,7 @@
                     <div class="btn-group">
                         <button class="btn btn-link" title="{{ 'Refresh' | T }}" ng-click="device.refresh()"><i class="fa fa-refresh"></i></button>
                         <button ng-if="user_auth_data.device.device.add" class="btn btn-link" title="{{ 'Create a device' | T }}" ng-click="device.addDevice()"><i class="fa fa-plus-circle"></i></button>
-                        <button class="btn btn-link" title="{{ 'Check Device Build Info' | T }}" ng-click="device.check()"><i class="fa fa-repeat"></i></button>
+                        <button class="btn btn-link" title="{{ 'Check Device Build Info' | T }}" ng-click="device.check()" ng-if="device.deviceList.length > 0"><i class="fa fa-repeat"></i></button>
                     </div>
                 </div>
             </div>
@@ -93,4 +93,4 @@
             </div>
         </div>
     </div>
-</div>
\ No newline at end of file
+</div>
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/device_group/device_group.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/device_group/device_group.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/device_group/device_group.controller.js	(working copy)
@@ -9,11 +9,14 @@
         '$uibModal',
         'deviceGroupService',
         'userAuthService',
-        function($scope, $rootScope, $state, $location, $filter, $uibModal, deviceGroupService, userAuthService) {
+        'localStorageService',
+        'roleMgmtService',
+        function($scope, $rootScope, $state, $location, $filter, $uibModal, deviceGroupService, userAuthService, localStorageService, roleMgmtService) {
             $rootScope.title = 'Device Group';
             //get user auth data
-            //here not use localStorageService, beacuse we want to get raw str
+            //here not use localStorageService, because we want to get raw str
             $scope.user_auth_data = userAuthService.build_auth_data(0, localStorage["auth_data"]);
+            $scope.role_info = localStorageService.getWebStorage('role_info');
 
             var deviceGroupTableView = this;
 
@@ -32,34 +35,9 @@
                 });
             };
 
-            deviceGroupTableView.get_device_group = function () {
-                deviceGroupService
-                .getDeviceGroup()
-                .then(function (res) {
-                    if (res && res.status === 200) {
-                        for (var i = res.data.length - 1; i >= 0; i--) {
-                            var device_list = [];
-                            if (res.data[i]["device_list"]) {
-                                for (var j = res.data[i]["device_list"].length - 1; j >= 0; j--) {
-                                    device_list.push(res.data[i]["device_list"][j]["ip"]);
-                                }
-                                res.data[i]["device_list"] = device_list.join(", ");
-                                res.data[i]["devices"] = device_list;
-                            } else {
-                                res.data[i]["device_list"] = "";
-                                res.data[i]["devices"] = [];
-                            }
-                        }
-                        deviceGroupTableView.tableData = res.data;
-                    }
-                });
-            };
-
-            deviceGroupTableView.get_device_group();
-
             deviceGroupTableView.refresh = function () {
                 deviceGroupTableView.tableData = undefined;
-                deviceGroupTableView.get_device_group();
+                getRoleDeviceGroupMapping();
             };
 
             deviceGroupTableView.showGroupAddModal = function () {
@@ -96,7 +74,7 @@
             };
 
             deviceGroupTableView.delete = function (row) {
-                reminder = confirm($filter('T')('If you delete the device group also deletes all devices bound to this device group. Are you sure you want to delete it?'));
+                let reminder = confirm($filter('T')('If you delete the device group also deletes all devices bound to this device group. Are you sure you want to delete it?'));
                 if (reminder) {
                     deviceGroupTableView.showProgressBar();
                     deviceGroupService
@@ -115,6 +93,51 @@
                         });
                 }
             };
+
+            function getRoleDeviceGroupMapping() {
+                deviceGroupTableView.deviceMap = [];
+                deviceGroupTableView.deviceGroupList = [];
+
+                // fetch the device group information for the specific role.
+                roleMgmtService.getRoleDeviceGroupMapping($scope.role_info).then(function (res) {
+                    if (res && res.status === 200) {
+                        try {
+                            let data = res.data;
+                            if (data.length > 1) {
+                                try {
+                                    let deviceMap = data[1]['result'];
+                                    deviceGroupTableView.deviceGroupList = deviceMap;
+                                    $scope.group_list = [];
+                                    deviceMap.forEach(function (deviceGroup) {
+                                        let device_list = '';
+                                        let devices = [];
+                                        $scope.group_list.push(deviceGroup['group_name']);
+                                        deviceGroup['device_list'].forEach(function (device) {
+                                            if (device_list !== '') {
+                                                device_list += ', '
+                                            }
+                                            device_list += device.ip;
+                                            devices.push(device.ip);
+                                        })
+                                        deviceGroupTableView.deviceMap.push({
+                                            name: deviceGroup['group_name'], device_list: device_list, devices: devices
+                                        })
+                                    })
+                                    deviceGroupTableView.tableData = deviceGroupTableView.deviceMap;
+                                } catch (e) {
+                                    console.error('Error getRoleDeviceGroupMapping returned error.' + e);
+                                    deviceGroupTableView.deviceMap = [];
+                                }
+                            }
+                        } catch (e) {
+                            console.log('500 - Internal server error.');
+                            alert('500 - Internal server error. Failed to fetch device group mapping info.');
+                        }
+                    }
+                });
+            }
+
+            getRoleDeviceGroupMapping();
         }
     ])
     .controller('deviceGroupAddCtrl', [
@@ -195,7 +218,7 @@
             deviceGroupManageView.modalClose = function () {
                 $uibModalInstance.dismiss();
             }
-            
+
             deviceService.getDeviceList().then(function (res) {
                 if (res && res.status === 200) {
                     var devices_list = [];
@@ -224,7 +247,7 @@
                         $rootScope.$broadcast('endLoading', true);
                         if (res&&res.status === 200) {
                             if (res.data[0]) {
-                                if (res.data[2] && res.data[2][0] && res.data[2][0][0] == "warning") {
+                                if (res.data[2] && res.data[2][0] && res.data[2][0][0] === "warning") {
                                     $rootScope.TipService.setMessage(res.data[2][0][1]);
                                 } else {
                                     $uibModalInstance.close(true);
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/device_group/device_group.html
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/device_group/device_group.html	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/device_group/device_group.html	(working copy)
@@ -1,47 +1,57 @@
-<div class="container-fluid"> 
-        <div class="row">
-            <rd-widget>
-                <rd-widget-header title="{{'Device Group'|T}}">
-                </rd-widget-header>
-                <div class="table-toolbar">
-                    <div class="">
-                        <div class="btn-group">
-                            <button title="{{'Refresh'|T}}" class="btn btn-link hive_enable_active" ng-click="table.refresh()"><i class="fa fa-refresh"></i></button>
-                            <button ng-if="user_auth_data.device.device_group.add" title="{{'Add a Device Group'|T}}" class="btn btn-link" ng-click="table.showGroupAddModal()"><i class="fa fa-plus-circle"></i></button>
-                        </div>
+<div class="container-fluid">
+    <div class="row">
+        <rd-widget>
+            <rd-widget-header title="{{'Device Group'|T}}">
+            </rd-widget-header>
+            <div class="table-toolbar">
+                <div class="">
+                    <div class="btn-group">
+                        <button title="{{'Refresh'|T}}" class="btn btn-link hive_enable_active"
+                                ng-click="table.refresh()"><i class="fa fa-refresh"></i></button>
+                        <button ng-if="role_info.user_type != 'Device Admin'" title="{{'Add a Device Group'|T}}"
+                                class="btn btn-link" ng-click="table.showGroupAddModal()"><i
+                            class="fa fa-plus-circle"></i></button>
                     </div>
-                    <div class="btn-group pull-right"></div>
                 </div>
-                <div class="table-container" st-table="displayedCollection" st-safe-src="table.tableData">
-                    <div class="table-responsive table-content">
-                        <table class="table table-striped table-hover">
-                            <thead>
-                            <tr>
-                                <th>No.</th>
-                                <th st-sort="name" style="cursor: pointer;">{{'Name'|T}}</th>
-                                <th st-sort="device" style="cursor: pointer; min-width: 120px;">{{'Managed Devices'|T}}</th>
-                                <th>{{'Action'|T}}</th>
-                            </tr>
-                            </thead>
-                            <tbody>
-                            <tr ng-repeat="row in displayedCollection">
-                                <td>{{ ((currentPageIndex - 1) * pageSize) + $index + 1 }}</td>
-                                <td>{{row.name}}</td>
-                                <td>{{row.device_list}}</td>
-                                <td>
-                                    <a ng-if="user_auth_data.device.device_group.delete" class="icon-box" style="cursor:pointer" title="{{'Delete'|T}}" ng-click="table.delete(row)"><i class="array-delete"></i></a>
-                                    <a ng-if="user_auth_data.device.device_group.delete" class="icon-box" style="cursor:pointer" title="{{'Manage Devices'|T}}" ng-click="table.manage(row)"><i class="array-edit"></i></a>
-                                </td>
-                            </tr>
-                            </tbody>
-                        </table>
-                    </div>
-                    <div style="margin-bottom: 15px;text-align: center" ng-hide="table.tableData"><img src="app/images/loading.gif"></div>
-                    <div class="table-pagination">
-                        <div class="pagination-detail"></div>
-                        <div class="pagination" st-pagination="" st-items-by-page="pageSize" st-displayed-pages="5" st-page-change="onPageChange(newPage)"></div>
-                    </div>
+                <div class="btn-group pull-right"></div>
+            </div>
+            <div class="table-container" st-table="displayedCollection" st-safe-src="table.tableData">
+                <div class="table-responsive table-content">
+                    <table class="table table-striped table-hover">
+                        <thead>
+                        <tr>
+                            <th>No.</th>
+                            <th st-sort="name" style="cursor: pointer;">{{'Name'|T}}</th>
+                            <th st-sort="device" style="cursor: pointer; min-width: 120px;">{{'Managed Devices'|T}}</th>
+                            <th>{{'Action'|T}}</th>
+                        </tr>
+                        </thead>
+                        <tbody>
+                        <tr ng-repeat="row in displayedCollection">
+                            <td>{{ ((currentPageIndex - 1) * pageSize) + $index + 1 }}</td>
+                            <td>{{row.name}}</td>
+                            <td>{{row.device_list}}</td>
+                            <td>
+                                <!--                                ToDo: Edit Device Group not working.-->
+                                <!--                                <a ng-if="role_info.user_type != 'Device Admin'" class="icon-box" style="cursor:pointer"-->
+                                <!--                                   title="{{'Manage Devices'|T}}" ng-click="table.manage(row)"><i-->
+                                <!--                                    class="array-edit"></i></a>-->
+                                <!--                                &nbsp;&nbsp;-->
+                                <a ng-if="role_info.user_type != 'Device Admin'" class="icon-box" style="cursor:pointer"
+                                   title="{{'Delete'|T}}" ng-click="table.delete(row)"><i class="array-delete"></i></a>
+                            </td>
+                        </tr>
+                        </tbody>
+                    </table>
+                </div>
+                <div style="margin-bottom: 15px;text-align: center" ng-hide="table.tableData"><img
+                    src="app/images/loading.gif"></div>
+                <div class="table-pagination">
+                    <div class="pagination-detail"></div>
+                    <div class="pagination" st-pagination="" st-items-by-page="pageSize" st-displayed-pages="5"
+                         st-page-change="onPageChange(newPage)"></div>
                 </div>
-            </rd-widget>
-        </div>
-    </div>
\ No newline at end of file
+            </div>
+        </rd-widget>
+    </div>
+</div>
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/device_group/device_group_add.html
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/device_group/device_group_add.html	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/device_group/device_group_add.html	(working copy)
@@ -10,7 +10,8 @@
                 <div class="form-group">
                     <label class="col-md-3 control-label">{{'Name'|T}}</label>
                     <div class="col-md-8">
-                        <input ng-verify="required:true, max:32, skip_chainese_verify:true" type="text" class="form-control" ng-model="deviceGroupAdd.data.name" name="name" >
+                        <input ng-verify="required:true, max:32, skip_chainese_verify:true" type="text"
+                               class="form-control" ng-model="deviceGroupAdd.data.name" name="name">
                     </div>
                 </div>
             </form>
@@ -18,6 +19,8 @@
     </div>
 </div>
 <div class="modal-footer">
-    <button ng-verify="control:'general'" type="button" class="btn btn-primary" ng-click="deviceGroupAdd.save(deviceGroupAdd.data)">{{'Save'|T}}</button>
+    <button ng-verify="control:'general'" type="button" class="btn btn-primary"
+            ng-click="deviceGroupAdd.save(deviceGroupAdd.data)">{{'Save'|T}}
+    </button>
     <button type="button" class="btn btn-default" ng-click="deviceGroupAdd.modalClose()">{{'Cancel'|T}}</button>
 </div>
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/device_group/device_group_manage.html
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/device_group/device_group_manage.html	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/device_group/device_group_manage.html	(working copy)
@@ -21,6 +21,8 @@
     </div>
 </div>
 <div class="modal-footer">
-    <button ng-verify="control:'general'" type="button" class="btn btn-primary" ng-click="deviceGroupManage.save(deviceGroupManage.data)">{{'Save'|T}}</button>
+    <button ng-verify="control:'general'" type="button" class="btn btn-primary"
+            ng-click="deviceGroupManage.save(deviceGroupManage.data)">{{'Save'|T}}
+    </button>
     <button type="button" class="btn btn-default" ng-click="deviceGroupManage.modalClose()">{{'Cancel'|T}}</button>
 </div>
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/image/modal/system-update.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/image/modal/system-update.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/image/modal/system-update.controller.js	(working copy)
@@ -12,8 +12,11 @@
         'deviceService',
         'deviceGroupService',
         'sysUpdateImageInfo',
-        function ($scope, $rootScope, $state, $stateParams, $uibModal, $uibModalInstance, $filter, apiService, imageTableService, deviceService, deviceGroupService, sysUpdateImageInfo) {
+        'roleMgmtService',
+        'localStorageService',
+        function ($scope, $rootScope, $state, $stateParams, $uibModal, $uibModalInstance, $filter, apiService, imageTableService, deviceService, deviceGroupService, sysUpdateImageInfo, roleMgmtService, localStorageService) {
 
+            $scope.role_info = localStorageService.getWebStorage('role_info');
             var sysUpdateViewModal = this;
             sysUpdateViewModal.isDeferred = false;
             sysUpdateViewModal.backup_db = false;
@@ -24,62 +27,65 @@
             sysUpdateViewModal.sysUpdateInfo = sysUpdateImageInfo;
             sysUpdateViewModal.isASFDevice = new Object();
             sysUpdateViewModal.asfProductName = ["asf", "vasf", 'netwaf', 'vnetwaf'];
-            
-            deviceService.getDeviceList().then(function (res) {
+
+            sysUpdateViewModal.deviceList = [];
+            sysUpdateViewModal.deviceGroupList = [];
+            // fetch the device group information for the specific role.
+            roleMgmtService.getRoleDeviceGroupMapping($scope.role_info).then(function (res) {
                 if (res && res.status === 200) {
-                    sysUpdateViewModal.deviceList = res.data;
-                    _.each(res.data, function(data){
-                        sysUpdateViewModal.isASFDevice[data['name']] = false;
-                        if (sysUpdateViewModal.asfProductName.indexOf(data['type'].toLowerCase()) != -1) {
-                            sysUpdateViewModal.isASFDevice[data['name']] = true;
+                    try {
+                        let data = res.data;
+                        if (data.length > 1) {
+                            try {
+                                let deviceMap = data[1]['result'];
+                                deviceMap.forEach(function (deviceGroup) {
+                                    deviceGroup['name'] = deviceGroup['group_name'];
+                                    deviceGroup['device_list'].forEach(function (device) {
+                                        sysUpdateViewModal.isASFDevice[device['name']] = false
+                                        if (sysUpdateViewModal.asfProductName.indexOf(device['type'].toLowerCase()) !== -1) {
+                                            sysUpdateViewModal.isASFDevice[data['name']] = true;
+                                        }
+                                        sysUpdateViewModal.deviceList.push(device);
+                                    })
+                                })
+                                sysUpdateViewModal.deviceGroupList = deviceMap;
+                            } catch (e) {
+                                console.error('Error getRoleDeviceGroupMapping returned error.' + e);
+                                sysUpdateViewModal.deviceList = []
+                                sysUpdateViewModal.deviceGroupList = [];
+                            }
                         }
-                    });
-                } else {
-                    sysUpdateViewModal.deviceList = [];
+                        if (sysUpdateViewModal.deviceGroupList.length > 0) sysUpdateViewModal.showDeviceGroup = true;
+                        if (sysUpdateViewModal.deviceList.length > 0)sysUpdateViewModal.showDevice = true;
+                    } catch (e) {
+                        console.log('500 - Internal server error.');
+                        alert('500 - Internal server error. Failed to fetch device group mapping info.');
+                    }
                 }
-                //data gotten, display the dropdown box
-                sysUpdateViewModal.showDevice = true;
             });
-    
-            deviceGroupService.getDeviceGroup().then(function (res) {
-                if (res && res.status === 200) {
-                    sysUpdateViewModal.deviceGroupList = $filter("FG")(res.data);
 
-                    _.each(res.data, function(data){
-                        sysUpdateViewModal.isASFDevice[data['name']] = false;
-                        _.each(data['device_list'], function(each_data){
-                            if (sysUpdateViewModal.asfProductName.indexOf(each_data['type'].toLowerCase()) != -1) {
-                                sysUpdateViewModal.isASFDevice[data['name']] = true;
-                            }
-                        });
-                    });
-                } else {
-                    sysUpdateViewModal.deviceGroupList = [];
-                }
-                sysUpdateViewModal.showDeviceGroup = true;
-            });
-            $scope.$watch(function() {
+            $scope.$watch(function () {
                 return sysUpdateViewModal.option;
-            },function(value) {
+            }, function (value) {
                 if (value == '2') {
                     sysUpdateViewModal.isDeferred = true;
                 } else {
                     sysUpdateViewModal.isDeferred = false;
                 }
             }, true);
-    
+
             sysUpdateViewModal.click_device = function () {
                 sysUpdateViewModal.showDeviceTab = true;
-                sysUpdateViewModal.checkDeviceType(sysUpdateViewModal.device||[]);
+                sysUpdateViewModal.checkDeviceType(sysUpdateViewModal.device || []);
             };
-    
+
             sysUpdateViewModal.click_device_group = function () {
                 sysUpdateViewModal.showDeviceTab = false;
-                sysUpdateViewModal.checkDeviceType(sysUpdateViewModal.device_group||[]);
+                sysUpdateViewModal.checkDeviceType(sysUpdateViewModal.device_group || []);
             };
-    
-            sysUpdateViewModal.checkDeviceType = function(device_name) {
-                for (var i=0; i<= device_name.length; i++) {
+
+            sysUpdateViewModal.checkDeviceType = function (device_name) {
+                for (var i = 0; i <= device_name.length; i++) {
                     if (sysUpdateViewModal.isASFDevice[device_name[i]]) {
                         sysUpdateViewModal.display_backup_db = true;
                         return;
@@ -87,7 +93,7 @@
                 }
                 sysUpdateViewModal.display_backup_db = false;
             }
-            var showProgressBar = function() {
+            var showProgressBar = function () {
                 var modalInstance = $uibModal.open({
                     templateUrl: 'app/modules/common/templates/progress.html',
                     controller: 'showProgressCtrl',
@@ -121,14 +127,14 @@
                 }
                 showProgressBar();
                 var sysUpdateInfoJSON = {
-                    "action" :"System_update",
-                    "options" : {
+                    "action": "System_update",
+                    "options": {
                         "__pk_list": [
                             JSON.stringify(
                                 {
-                                    "app_name" : sysUpdateViewModal.sysUpdateInfo.app_name,
-                                    "build_version" : sysUpdateViewModal.sysUpdateInfo.build_version,
-                                    "id" : sysUpdateViewModal.sysUpdateInfo.id
+                                    "app_name": sysUpdateViewModal.sysUpdateInfo.app_name,
+                                    "build_version": sysUpdateViewModal.sysUpdateInfo.build_version,
+                                    "id": sysUpdateViewModal.sysUpdateInfo.id
                                 }
                             )
                         ]
@@ -137,11 +143,11 @@
                 //device
                 if (sysUpdateViewModal.showDeviceTab) {
                     sysUpdateInfoJSON.options.devices = {
-                        'device' : sysUpdateViewModal.device
+                        'device': sysUpdateViewModal.device
                     };
                 } else {
                     sysUpdateInfoJSON.options.devices = {
-                        'group' : sysUpdateViewModal.device_group
+                        'group': sysUpdateViewModal.device_group
                     };
                 }
                 //sysUpdateInfoJSON.options.devices = JSON.stringify(sysUpdateInfoJSON.options.devices);
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/login/login.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/login/login.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/login/login.controller.js	(working copy)
@@ -146,6 +146,15 @@
                                     }
                                 });
 
+                                userMgmtService.getUserRoleInfo(loginData.username).then(function(res) {
+                                    if (res && res.status === 200) {
+                                        if (res.data.length > 0) {
+                                            $rootScope.role_info = res.data[1]['result'];
+                                            localStorageService.setWebStorage("role_info", $rootScope.role_info);
+                                        }
+                                    }
+                                })
+
                                 // reset composer language
                                 cmService.get_composer_language().then(function(res) {
                                     var default_lang = CMSettings.language[0].name;
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/main/main.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/main/main.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/main/main.controller.js	(working copy)
@@ -8,7 +8,7 @@
         function ($scope, $rootScope, TipService, CMSettings) {
             var default_theme = CMSettings.theme[0].name;
             var default_lang = CMSettings.language[0].name;
-            if ( !window.localStorage.theme ) {
+            if (!window.localStorage.theme) {
                 window.localStorage.theme = default_theme;
             }
             if (!window.localStorage.lang) {
@@ -36,15 +36,15 @@
             $rootScope.title = 'AMP';
             $rootScope.showSideBar = true;
 
-            $scope.root_menu_active = function(url_prefix){
-                if (typeof(url_prefix) == 'string') {
-                    if($location.path().indexOf(url_prefix) === 0){
+            $scope.root_menu_active = function (url_prefix) {
+                if (typeof (url_prefix) == 'string') {
+                    if ($location.path().indexOf(url_prefix) === 0) {
                         return true;
                     }
                 } else {
                     var result = false;
-                    _.each(url_prefix, function(url){
-                        if($location.path().indexOf(url) === 0){
+                    _.each(url_prefix, function (url) {
+                        if ($location.path().indexOf(url) === 0) {
                             result = true;
                             return false; //this means break
                         }
@@ -57,29 +57,29 @@
             $scope.url_contain = function (url) {
                 if ($location.path().indexOf(url) != -1) {
                     // we should avoid these following cases when implementing the router, but making special now.
-                    // To avoid the case when url is "device" but location is "device-group", 
+                    // To avoid the case when url is "device" but location is "device-group",
                     // both "device" and "device-group" sidebar will be highlighted.
                     if ($location.path().indexOf('device_group') != -1) {
-                        if(url.indexOf('device_group') == -1 ) {
+                        if (url.indexOf('device_group') == -1) {
                             return false;
                         }
                     }
-                    // To avoid the case when url is "device" but location is "/configuration/device", 
+                    // To avoid the case when url is "device" but location is "/configuration/device",
                     // both "device" and "/configuration/device" sidebar will be highlighted.
                     if ($location.path().indexOf('/configuration/device') != -1) {
-                        if(url.indexOf('/configuration/device') == -1 ) {
+                        if (url.indexOf('/configuration/device') == -1) {
                             return false;
                         }
                     }
-                    // To avoid the case when url is "system" but location is "/configuration/system", 
+                    // To avoid the case when url is "system" but location is "/configuration/system",
                     // both "system" and "/configuration/system" sidebar will be highlighted.
                     if ($location.path().indexOf('/configuration/system') != -1) {
-                        if(url.indexOf('/configuration/system') == -1 ) {
+                        if (url.indexOf('/configuration/system') == -1) {
                             return false;
                         }
                     }
                     if ($location.path().indexOf('/volume_license/device') != -1) {
-                        if(url.indexOf('/volume_license/device') == -1 ) {
+                        if (url.indexOf('/volume_license/device') == -1) {
                             return false;
                         }
                     }
@@ -88,7 +88,7 @@
                 return false;
             };
 
-            SBViewModel.show_or_hide = function(){
+            SBViewModel.show_or_hide = function () {
                 // if ( $location.path().indexOf("/monitor") == 0 ) {
                 //     $rootScope.showSecond = true;
                 // }
@@ -96,7 +96,7 @@
 
             };
 
-            SBViewModel.show_or_hide_by_submenu = function(state1, state2){
+            SBViewModel.show_or_hide_by_submenu = function (state1, state2) {
                 $rootScope.showSideBar = state1;
                 if (state2 && !state1) {
                     $rootScope.showSecond = true;
@@ -111,7 +111,7 @@
                     if (res && res.status == 200) {
                         var m = [];
                         var n = [];
-                        _.each(res.data, function(each){
+                        _.each(res.data, function (each) {
                             if (each.has_webui) {
                                 var each_sidebar = each['webui_sidebar'];
                                 each_sidebar.name = each.name;
@@ -122,13 +122,13 @@
                                         m.push(each_sidebar);
                                     } else {
                                         n.push(each_sidebar);
-                                    }        
+                                    }
                                 }
                             }
                         });
                         SBViewModel.extensions = m;
                         // for those with parents, we should update them into their parents' json
-                        _.each(n, function(d){
+                        _.each(n, function (d) {
                             _.each(SBViewModel.main, function (main) {
                                 if (main.name == d.parent) {
                                     main.elements.push(d);
@@ -141,11 +141,11 @@
                             });
                         });
                     }
-                    
+                    check_sidebar_auth();
                 });
             };
             var check_sidebar_auth = function () {
-                _.each(SBViewModel.main, function(main) {
+                _.each(SBViewModel.main, function (main) {
                     if (main.auth_path) {
                         if (userAuthService.check_user_auth(main.auth_path)) {
                             main.show = true;
@@ -154,7 +154,7 @@
                         }
                     } // if no auth_path defined, do nothing
                     if (main.elements) {
-                        _.each(main.elements, function(ele) {
+                        _.each(main.elements, function (ele) {
                             if (ele.auth_path) {
                                 if (userAuthService.check_user_auth(ele.auth_path)) {
                                     ele.show = true;
@@ -163,8 +163,8 @@
                                 }
                             } // if no auth_path defined, do nothing
                             if (ele.submenu && ele.submenu.list) {
-                                var main_show=false;
-                                _.each(ele.submenu.list, function(sub) {
+                                var main_show = false;
+                                _.each(ele.submenu.list, function (sub) {
                                     if (sub.auth_path) {
                                         if (userAuthService.check_user_auth(sub.auth_path)) {
                                             sub.show = true;
@@ -184,36 +184,74 @@
                     }
                 });
                 // Checking twice to hide parent title when all elements are hidden
-                _.each(SBViewModel.main, function(main) {
+                _.each(SBViewModel.main, function (main) {
                     var parent_title_show_flag = false;
-                    _.each(main.elements, function(ele) {
+                    _.each(main.elements, function (ele) {
                         parent_title_show_flag = parent_title_show_flag | ele.show;
                     });
                     main.show = parent_title_show_flag;
                 });
+                // Extensions
+                _.each(SBViewModel.extensions, function (extension) {
+                    if (extension.auth_path) {
+                        extension.show = userAuthService.check_user_auth(extension.auth_path);
+                    } // if no auth_path defined, do nothing
+                    if (extension.elements) {
+                        _.each(extension.elements, function (ele) {
+                            if (ele.auth_path) {
+                                ele.show = userAuthService.check_user_auth(ele.auth_path);
+                            } // if no auth_path defined, do nothing
+                            if (ele.submenu && ele.submenu.list) {
+                                var extension_show = false;
+                                _.each(ele.submenu.list, function (sub) {
+                                    if (sub.auth_path) {
+                                        if (userAuthService.check_user_auth(sub.auth_path)) {
+                                            sub.show = true;
+                                            extension_show = true;
+                                        } else {
+                                            sub.show = false;
+                                        }
+                                    } else {
+                                        // if no auth_path defined, always show
+                                        sub.show = true;
+                                        extension_show = true;
+                                    }
+                                });
+                                ele.show = extension_show;
+                            }
+                        });
+                    }
+                });
+                // Checking twice to hide parent title when all elements are hidden
+                _.each(SBViewModel.extensions, function (extension) {
+                    var parent_title_show_flag = false;
+                    _.each(extension.elements, function (ele) {
+                        parent_title_show_flag = parent_title_show_flag || ele.show;
+                    });
+                    extension.show = parent_title_show_flag;
+                });
             };
 
             var render_sidebar = function () {
                 get_extensions();
-                check_sidebar_auth();
             };
 
             render_sidebar();
 
-            $scope.$on('sidebar',function(event, data){
+            $scope.$on('sidebar', function (event, data) {
                 render_sidebar();
             });
 
-            $scope.$watch(function() {
+            $scope.$watch(function () {
                 return $rootScope.user_auth;
-            },function(newValue, oldValue, scope) {
+            }, function (newValue, oldValue, scope) {
                 //when user auth is changed by super admin
                 // 1. should render sidebar again
                 // 2. should update local storage
                 // 3. should parse auth data again
                 if (oldValue && newValue && oldValue.auth != newValue.auth) {
                     $rootScope.auth_data = userAuthService.build_auth_data(0, $rootScope.user_auth.auth);
-                    localStorageService.setWebStorage("user_auth", $rootScope.user_auth); 
+                    localStorageService.setWebStorage("user_auth", $rootScope.user_auth);
                     localStorageService.setWebStorage("auth_data", $rootScope.auth_data);
                     render_sidebar();
                 }
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/main/navbar.html
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/main/navbar.html	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/main/navbar.html	(working copy)
@@ -129,7 +129,7 @@
                 <li class="nav-item" uib-dropdown>
                     <a href="" uib-dropdown-toggle><i title="{{ 'Account' | T }}" class="fa array-profile"></i></a>
                     <ul class="dropdown-menu">
-                        <li class="dropdown-header" ng-controller="currentUserCtrl">{{ user }} ({{root?'Super Admin':'Common Admin'|T}})</li>
+                        <li class="dropdown-header" ng-controller="currentUserCtrl">{{ user }} ({{root?'Super Admin':'Admin'|T}})</li>
                         <li class="divider"></li>
                         <li class="link">
                             <a title="Logout" href="" ng-controller="ManualLogoutCtrl" ng-click="logout()">
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/slb_topology/real_service/real_service.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/slb_topology/real_service/real_service.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/slb_topology/real_service/real_service.controller.js	(working copy)
@@ -34,15 +34,15 @@
         'localStorageService',
         'slbTopologyService',
         'userAuthService',
-        'deviceService',
         'FileUploader',
-        function ($scope, $rootScope, $state, $stateParams, $location, $uibModal, $aside, deviceService, $filter, $timeout, localStorageService, slbTopologyService, userAuthService, deviceService, FileUploader) {
+        'roleMgmtService',
+        function ($scope, $rootScope, $state, $stateParams, $location, $uibModal, $aside, deviceService, $filter, $timeout, localStorageService, slbTopologyService, userAuthService, FileUploader, roleMgmtService) {
             $rootScope.title = 'Real Service';
 
             //get user auth data
             //here not use localStorageService, beacuse we want to get raw str
             $scope.user_auth_data = userAuthService.build_auth_data(0, localStorage["auth_data"]);
-
+            $scope.role_info = localStorageService.getWebStorage('role_info');
             var serviceViewModel = this;
 
             var user_info = localStorageService.getWebStorage("user_info");
@@ -58,23 +58,35 @@
             serviceViewModel.blockName = "";
             serviceViewModel.deviceName = "";
 
-            deviceService.getDeviceList().then(function (res) {
-                var deviceList = [];
-                var device_type_info = localStorageService.getWebStorage("device_type_info");
-                if (res && res.status === 200 && res.data instanceof Array) {
-                    _.each(res.data, function (host) {
-                        if (device_type_info.ADC_TYPE_LIST.indexOf(host.type.toLowerCase()) != -1) {
-                            deviceList.push(host.name)
+            roleMgmtService.getRoleDeviceGroupMapping($scope.role_info).then(function (res) {
+                serviceViewModel.deviceList = [];
+                let device_type_info = localStorageService.getWebStorage("device_type_info");
+                if (res && res.status === 200) {
+                    let data = res.data;
+                    if (data.length > 1) {
+                        try {
+                            let deviceMap = data[1]['result'];
+                            let device_list = [];
+                            deviceMap.forEach(function (deviceGroup) {
+                                deviceGroup['device_list'].forEach(function (device) {
+                                    if (device_type_info.ADC_TYPE_LIST.indexOf(device.type.toLowerCase()) !== -1) {
+                                        device_list.push(device.name)
+                                    }
+                                })
+                            })
+                            serviceViewModel.deviceList = device_list;
+                        } catch (e) {
+                            console.error('Error getRoleDeviceGroupMapping returned error.' + e);
                         }
-                    });
+                    }
                 }
-                serviceViewModel.deviceList = deviceList;
             });
 
             serviceViewModel.refreshBlock = function () {
                 serviceViewModel.blockLoading = true;
                 slbTopologyService.getRealServiceBlock().then(function (res) {
                     if (res && res.status === 200) {
+                        console.log(res.data);
                         serviceViewModel.blockLoading = false;
                         serviceViewModel.blocks = res.data.blocks;
                     }
@@ -85,7 +97,8 @@
             serviceViewModel.refresh = function () {
                 serviceViewModel.loading = true;
                 serviceViewModel.all = false;
-                slbTopologyService.getAllRealService().then(function (res) {
+                $scope.role_info = localStorageService.getWebStorage('role_info');
+                slbTopologyService.getAllRealService($scope.role_info).then(function (res) {
                     serviceViewModel.loading = false;
                     var deviceList = []
                     var serviceList = [];
@@ -510,7 +523,8 @@
         '$filter',
         'slbTopologyService',
         'modalData',
-        function ($scope, $rootScope, $state, $stateParams, $uibModal, $uibModalInstance, $filter, slbTopologyService, modalData) {
+        'localStorageService',
+        function ($scope, $rootScope, $state, $stateParams, $uibModal, $uibModalInstance, $filter, slbTopologyService, modalData, localStorageService) {
             var modalViewModel = this;
             modalViewModel.modalClose = function () {
                 $uibModalInstance.dismiss();
@@ -534,7 +548,7 @@
                     }))
                 })
             }
-            
+
             modalViewModel.verboseName = function(row){
 
                 console.log($filter("T")("No Block"))
@@ -546,7 +560,8 @@
 
             modalViewModel.loading = true;
             modalViewModel.serviceList = [];
-            slbTopologyService.getAllRealService().then(function (res) {
+            $scope.role_info = localStorageService.getWebStorage('role_info');
+            slbTopologyService.getAllRealService($scope.role_info).then(function (res) {
                 modalViewModel.loading = false;
                 var serviceList = [];
                 var errMessage = [];
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/slb_topology/slb_topology.service.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/slb_topology/slb_topology.service.js	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/slb_topology/slb_topology.service.js	(working copy)
@@ -13,23 +13,32 @@
                 getRealServiceBlock: getRealServiceBlock,
                 postRealServiceBlock: postRealServiceBlock,
             };
-            
+
             function getAllVirtualService(device_name) {
                 return api.proxy_get_dev(device_name, "/webui_utils/''");
             }
+
             function getVsTopology(vs_name, device_name) {
                 return api.proxy_get_dev(device_name, "/webui_utils/'" + vs_name + "'");
             }
-            function getAllRealService(){
-                return api.get('/real_service');
+
+            function getAllRealService(roleInfo) {
+                let roleId = roleInfo["role_id"];
+                if (roleId === null) {
+                    roleId = 0;
+                }
+                return api.get('/real_service?role_id=' + roleId);
             }
-            function postAllRealService(data){
+
+            function postAllRealService(data) {
                 return api.post2('/real_service', data);
             }
-            function getRealServiceBlock(){
+
+            function getRealServiceBlock() {
                 return api.get('/rs_block');
             }
-            function postRealServiceBlock(data){
+
+            function postRealServiceBlock(data) {
                 return api.post2('/rs_block', data);
             }
         }
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/slb_topology/virtual_service/virtual_service.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/slb_topology/virtual_service/virtual_service.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/slb_topology/virtual_service/virtual_service.controller.js	(working copy)
@@ -12,10 +12,11 @@
         'localStorageService',
         'slbTopologyService',
         'CMSettings',
-        function ($scope, $rootScope, $state, $stateParams, $location, $uibModal, $aside, deviceService, $filter, localStorageService, slbTopologyService, CMSettings) {
+        'roleMgmtService',
+        function ($scope, $rootScope, $state, $stateParams, $location, $uibModal, $aside, deviceService, $filter, localStorageService, slbTopologyService, CMSettings, roleMgmtService) {
             $rootScope.title = 'SLB Topology';
             var serviceViewModel = this;
-
+            $scope.role_info = localStorageService.getWebStorage('role_info');
             $scope.currentPageIndex = 1;
             $scope.pageSize = 20;
             $scope.onPageChange = function (newPage) {
@@ -23,7 +24,6 @@
             };
 
             serviceViewModel.app = CMSettings.app;
-            console.log(serviceViewModel.app);
 
             serviceViewModel.host_list = undefined;
             serviceViewModel.all_loadings = {};
@@ -31,7 +31,7 @@
                 if (serviceViewModel.serviceList === undefined) {
                     return true;
                 }
-                for(var i in serviceViewModel.all_loadings){
+                for (var i in serviceViewModel.all_loadings) {
                     if (!serviceViewModel.all_loadings[i]) {
                         return false;
                     }
@@ -43,7 +43,7 @@
                     serviceViewModel.host_list = undefined;
                     serviceViewModel.all_loadings = {};
                     serviceViewModel.serviceList = [];
-                    getServiceList ();
+                    getServiceList();
                 }
             }
             serviceViewModel.setDetail = function (device) {
@@ -54,174 +54,188 @@
                 }
                 window.localStorage.__deviceKey__ = JSON.stringify(deviceKey);
             }
-            function getServiceList_bc () {
+
+            function getServiceList_bc() {
                 localStorageService.setWebStorage("slb_service_previous_data", undefined);
                 deviceService
                     .getDeviceList()
-                    .then(function(res){
-                        if (res&&res.status === 200) {
+                    .then(function (res) {
+                        if (res && res.status === 200) {
                             serviceViewModel.host_list = res.data;
                             serviceViewModel.serviceList = [];
-                            _.each(serviceViewModel.host_list, function(host) {
+                            _.each(serviceViewModel.host_list, function (host) {
                                 serviceViewModel.all_loadings[host.name] = false;
                                 if (host.connection) {
                                     slbTopologyService
-                                    .getAllVirtualService(host.id)
-                                    .then(function(res) {
-                                        serviceViewModel.all_loadings[host.name] = true;
-                                        if (res && res.status === 200 && res.data.result) {
-                                            _.each(res.data.data, function(data) {
-                                                if (data.basic.protocol == 'vlink' || data.basic.service_name.indexOf("@@") != -1) {
-                                                    return;
-                                                }
-                                                var tmp = {
-                                                    "name":data.basic.service_name,
-                                                    "type":data.basic.protocol,
-                                                    "device":host.name,
-                                                    "ip":data.basic.vip,
-                                                    "policy":[],
-                                                    "group":[],
-                                                    "rs":[]
-                                                }
-                                                _.each(data.policies, function(pc) {
-                                                    if (pc.type == "static") {
-                                                        tmp["policy"].push("StaticPolicy");
-                                                        if (tmp["rs"].indexOf(pc.dst.name) == -1) {
-                                                            tmp["rs"].push(pc.dst.name);
-                                                        }
-                                                        
-                                                    } else {
-                                                        tmp["policy"].push(pc.name);
-                                                        if (pc.dst.type == "group") {
-                                                            if (tmp["group"].indexOf(pc.dst.name) == -1) {
-                                                                tmp["group"].push(pc.dst.name);
-                                                                _.each(pc.dst.members, function(rs) {
-                                                                    if (tmp["rs"].indexOf(rs.name) == -1) {
-                                                                        tmp["rs"].push(rs.name);
-                                                                    }
-                                                                });
+                                        .getAllVirtualService(host.id)
+                                        .then(function (res) {
+                                            serviceViewModel.all_loadings[host.name] = true;
+                                            if (res && res.status === 200 && res.data.result) {
+                                                _.each(res.data.data, function (data) {
+                                                    if (data.basic.protocol == 'vlink' || data.basic.service_name.indexOf("@@") != -1) {
+                                                        return;
+                                                    }
+                                                    var tmp = {
+                                                        "name": data.basic.service_name,
+                                                        "type": data.basic.protocol,
+                                                        "device": host.name,
+                                                        "ip": data.basic.vip,
+                                                        "policy": [],
+                                                        "group": [],
+                                                        "rs": []
+                                                    }
+                                                    _.each(data.policies, function (pc) {
+                                                        if (pc.type == "static") {
+                                                            tmp["policy"].push("StaticPolicy");
+                                                            if (tmp["rs"].indexOf(pc.dst.name) == -1) {
+                                                                tmp["rs"].push(pc.dst.name);
+                                                            }
+
+                                                        } else {
+                                                            tmp["policy"].push(pc.name);
+                                                            if (pc.dst.type == "group") {
+                                                                if (tmp["group"].indexOf(pc.dst.name) == -1) {
+                                                                    tmp["group"].push(pc.dst.name);
+                                                                    _.each(pc.dst.members, function (rs) {
+                                                                        if (tmp["rs"].indexOf(rs.name) == -1) {
+                                                                            tmp["rs"].push(rs.name);
+                                                                        }
+                                                                    });
+                                                                }
+
                                                             }
-                                                            
                                                         }
+                                                    });
+                                                    tmp.policy = tmp.policy.join(',');
+                                                    tmp.group = tmp.group.join(',');
+                                                    tmp.rs = tmp.rs.join(',');
+                                                    serviceViewModel.serviceList.push(tmp);
+                                                    if (serviceViewModel.get_loading()) {
+                                                        localStorageService.setWebStorage("slb_service_previous_data", serviceViewModel.serviceList);
                                                     }
                                                 });
-                                                tmp.policy = tmp.policy.join(',');
-                                                tmp.group = tmp.group.join(',');
-                                                tmp.rs = tmp.rs.join(',');
-                                                serviceViewModel.serviceList.push(tmp);
-                                                if (serviceViewModel.get_loading()) {
-                                                    localStorageService.setWebStorage("slb_service_previous_data", serviceViewModel.serviceList);
-                                                }
-                                            });
-                                        } else {
-                                            //error
-                                        }
-                                    });
+                                            } else {
+                                                //error
+                                            }
+                                        });
                                 } else {
                                     serviceViewModel.all_loadings[host.name] = true;
                                 }
                             });
                         }
-                    }); 
+                    });
             }
-            function getServiceList () {
+
+            function getServiceList() {
+                serviceViewModel.host_list = [];
+                serviceViewModel.serviceList = [];
                 localStorageService.setWebStorage("slb_service_previous_data", "");
-                deviceService
-                    .getDeviceList()
-                    .then(function(res){
-                        if (res&&res.status === 200) {
-                            serviceViewModel.host_list = res.data;
-                            serviceViewModel.serviceList = [];
-                            _.each(serviceViewModel.host_list, function(host) {
-                                serviceViewModel.all_loadings[host.name] = false;
-                                if (host.connection) {
-                                    slbTopologyService
-                                    .getAllVirtualService(host.id)
-                                    .then(function(res) {
-                                        serviceViewModel.all_loadings[host.name] = true;
-                                        if (res && res.status === 200 && res.data.result) {
-                                            _.each(res.data.data, function(data) {
-                                                if (data.basic.protocol == 'vlink' || data.basic.service_name.indexOf("@@") != -1) {
-                                                    return;
-                                                }
-                                                var tmp = {
-                                                    "name":data.basic.service_name,
-                                                    "type":data.basic.protocol,
-                                                    "device":host,
-                                                    "ip":data.basic.vip,
-                                                    "policy":{},
-                                                    "policy_num":0,
-                                                    "device_group": host.device_group,
-                                                    "device_name": host.name
-                                                }
-                                                _.each(data.policies, function(pc) {
-                                                    tmp["policy_num"] += 1;
-                                                    if (pc.type == "static") {
-                                                        tmp["policy"]["StaticPolicy"] = {
-                                                            "name": "StaticPolicy",
-                                                            "group" : "",
-                                                            "rs" : pc.dst.name
-                                                        };
-                                                    } else {
-                                                        if (pc.dst.type == "group") {
-                                                            tmp["policy"][pc.name] = {
-                                                                "name": pc.name,
-                                                                "group":"",
-                                                                "rs":[]
+                roleMgmtService.getRoleDeviceGroupMapping($scope.role_info).then(function (res) {
+                    if (res && res.status === 200) {
+                        let data = res.data;
+                        if (data.length > 1) {
+                            try {
+                                let deviceMap = data[1]['result'];
+                                deviceMap.forEach(function (deviceGroup) {
+                                    deviceGroup['device_list'].forEach(function (device) {
+                                        serviceViewModel.host_list.push(device)
+                                    })
+                                })
+                                _.each(serviceViewModel.host_list, function (host) {
+                                    serviceViewModel.all_loadings[host.name] = false;
+                                    if (host.connection) {
+                                        slbTopologyService
+                                            .getAllVirtualService(host.id)
+                                            .then(function (res) {
+                                                serviceViewModel.all_loadings[host.name] = true;
+                                                if (res && res.status === 200 && res.data.result) {
+                                                    _.each(res.data.data, function (data) {
+                                                        if (data.basic.protocol === 'vlink' || data.basic.service_name.indexOf("@@") !== -1) {
+                                                            return;
+                                                        }
+                                                        var tmp = {
+                                                            "name": data.basic.service_name,
+                                                            "type": data.basic.protocol,
+                                                            "device": host,
+                                                            "ip": data.basic.vip,
+                                                            "policy": {},
+                                                            "policy_num": 0,
+                                                            "device_group": host.device_group,
+                                                            "device_name": host.name
+                                                        }
+                                                        _.each(data.policies, function (pc) {
+                                                            tmp["policy_num"] += 1;
+                                                            if (pc.type === "static") {
+                                                                tmp["policy"]["StaticPolicy"] = {
+                                                                    "name": "StaticPolicy",
+                                                                    "group": "",
+                                                                    "rs": pc.dst.name
+                                                                };
+                                                            } else {
+                                                                if (pc.dst.type === "group") {
+                                                                    tmp["policy"][pc.name] = {
+                                                                        "name": pc.name,
+                                                                        "group": "",
+                                                                        "rs": []
+                                                                    }
+                                                                    tmp["policy"][pc.name]["group"] = pc.dst.name;
+                                                                    _.each(pc.dst.members, function (rs) {
+                                                                        tmp["policy"][pc.name]["rs"].push(rs.name);
+                                                                    });
+                                                                    tmp["policy"][pc.name]["rs"] = tmp["policy"][pc.name]["rs"].join(",");
+                                                                } else {
+                                                                    if (pc.dst.type === "vlink") {
+                                                                        tmp["policy"][pc.name] = {
+                                                                            "name": pc.name,
+                                                                            "group": "Vlink - " + pc.dst.name,
+                                                                            "rs": ""
+                                                                        }
+                                                                    }
+                                                                }
                                                             }
-                                                            tmp["policy"][pc.name]["group"] = pc.dst.name;
-                                                            _.each(pc.dst.members, function(rs) {
-                                                                tmp["policy"][pc.name]["rs"].push(rs.name);
-                                                            });
-                                                            tmp["policy"][pc.name]["rs"] = tmp["policy"][pc.name]["rs"].join(",");
-                                                        } else {
-                                                            if (pc.dst.type == "vlink") {
-                                                                tmp["policy"][pc.name] = {
+                                                        });
+                                                        if (tmp["policy_num"] === 1) {
+                                                            _.each(tmp["policy"], function (pc) {
+                                                                tmp["policy"] = {
                                                                     "name": pc.name,
-                                                                    "group":"Vlink - " + pc.dst.name,
-                                                                    "rs":""
+                                                                    "group": pc.group,
+                                                                    "rs": pc.rs
                                                                 }
+                                                            })
+                                                        }
+                                                        if (tmp["policy_num"] === 0) {
+                                                            tmp["policy"] = {
+                                                                "name": "",
+                                                                "group": "",
+                                                                "rs": ""
                                                             }
                                                         }
-                                                    }
-                                                });
-                                                if (tmp["policy_num"] == 1) {
-                                                    _.each(tmp["policy"], function(pc){
-                                                        tmp["policy"] = {
-                                                            "name":pc.name,
-                                                            "group":pc.group,
-                                                            "rs":pc.rs
+                                                        serviceViewModel.serviceList.push(tmp);
+                                                        if (serviceViewModel.get_loading()) {
+                                                            localStorageService.setWebStorage("slb_service_previous_data", serviceViewModel.serviceList);
                                                         }
-                                                    })
-                                                }
-                                                if (tmp["policy_num"] == 0) {
-                                                    tmp["policy"] = {
-                                                        "name":"",
-                                                        "group":"",
-                                                        "rs":""
-                                                    }
-                                                }
-                                                serviceViewModel.serviceList.push(tmp);
-                                                if (serviceViewModel.get_loading()) {
-                                                    localStorageService.setWebStorage("slb_service_previous_data", serviceViewModel.serviceList);
+                                                    });
+                                                } else {
+                                                    //error
                                                 }
                                             });
-                                        } else {
-                                            //error
-                                        }
-                                    });
-                                } else {
-                                    serviceViewModel.all_loadings[host.name] = true;
-                                }
-                            });
+                                    } else {
+                                        serviceViewModel.all_loadings[host.name] = true;
+                                    }
+                                });
+                            } catch (e) {
+                                console.error('Error getRoleDeviceGroupMapping returned error.' + e);
+                            }
                         }
-                    }); 
+                    }
+                });
             }
+
             var previous_page = localStorageService.getWebStorage("previous_page");
             if (previous_page && previous_page.url) {
                 if (previous_page.url == '/slb_topology/detail/{device}/{name}') {
                     var previous_data = localStorageService.getWebStorage("slb_service_previous_data");
-                    if (previous_data != undefined && typeof(previous_data) == "object") {
+                    if (previous_data != undefined && typeof (previous_data) == "object") {
                         serviceViewModel.serviceList = previous_data;
                     } else {
                         getServiceList();
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/ssl_monitoring/ssl.controller.js
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/ssl_monitoring/ssl.controller.js	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/client/app/modules/ssl_monitoring/ssl.controller.js	(working copy)
@@ -10,9 +10,10 @@
         'localStorageService',
         '$filter',
         'CMSettings',
-        function ($rootScope, $scope, $state, $stateParams, $uibModal, deviceService, sslMonitoringService, localStorageService, $filter, CMSettings) {
+        'roleMgmtService',
+        function ($rootScope, $scope, $state, $stateParams, $uibModal, deviceService, sslMonitoringService, localStorageService, $filter, CMSettings, roleMgmtService) {
             $rootScope.title = 'SSL Certificate';
-
+            $scope.role_info = localStorageService.getWebStorage('role_info');
             $scope.currentPageIndex = 1;
             $scope.pageSize = 20;
             $scope.onPageChange = function (newPage) {
@@ -37,80 +38,94 @@
 
             var device_type_info = localStorageService.getWebStorage("device_type_info");
             function getServiceList () {
-                deviceService
-                    .getDeviceList()
-                    .then(function(res){
-                        if (res&&res.status === 200) {
-                            tableViewModel.host_list = res.data;
-                            _.each(tableViewModel.host_list, function(host) {
-                                tableViewModel.all_loadings[host.name] = false;
-                                if (host.connection && device_type_info.ADC_TYPE_LIST.indexOf(host.type.toLowerCase()) != -1) {
-                                    var service_dict = {};
-                                    var service_done = false;
-                                    var vhost_done = false;
-                                    sslMonitoringService
-                                        .getVSList(host.id)
-                                        .then(function(res) {
-                                            service_done = true;
-                                            if (service_done && vhost_done) {
-                                                tableViewModel.all_loadings[host.name] = true;
-                                            }
-                                            _.each(res, function(data) {
-                                                if (data.service_name in service_dict) {
-                                                    service_dict[data.service_name]["type"] = data.protocol;
-                                                } else {
-                                                    service_dict[data.service_name] = {
-                                                        "name":data.service_name,
-                                                        "type":data.protocol,
-                                                        "device":host.name,
-                                                        "device_group":host.device_group,
-                                                        "host":"",
-                                                        "status":""
-                                                    };
-                                                }
+                tableViewModel.host_list = [];
+                // fetch the device group information for the specific role.
+                roleMgmtService.getRoleDeviceGroupMapping($scope.role_info).then(function (res) {
+                    if (res && res.status === 200) {
+                        try {
+                            let data = res.data;
+                            if (data.length > 1) {
+                                let deviceMap = data[1]['result'];
+                                deviceMap.forEach(function (deviceGroup) {
+                                    deviceGroup['device_list'].forEach(function (device) {
+                                        tableViewModel.host_list.push(device);
+                                    });
+                                });
+                                _.each(tableViewModel.host_list, function (host) {
+                                    tableViewModel.all_loadings[host.name] = false;
+                                    if (host.connection && device_type_info.ADC_TYPE_LIST.indexOf(host.type.toLowerCase()) != -1) {
+                                        var service_dict = {};
+                                        var service_done = false;
+                                        var vhost_done = false;
+                                        sslMonitoringService
+                                            .getVSList(host.id)
+                                            .then(function (res) {
+                                                service_done = true;
                                                 if (service_done && vhost_done) {
-                                                    tableViewModel.sslDataList.push(service_dict[data.service_name]);
+                                                    tableViewModel.all_loadings[host.name] = true;
                                                 }
-                                            });
-                                        });
-                                    sslMonitoringService
-                                        .getVhostList(host.id)
-                                        .then(function(res) {
-                                            vhost_done = true;
-                                            if (service_done && vhost_done) {
-                                                tableViewModel.all_loadings[host.name] = true;
-                                            }
-                                            _.each(res, function(data) {
-                                                if (data.service_name) {
+                                                _.each(res, function (data) {
                                                     if (data.service_name in service_dict) {
-                                                        service_dict[data.service_name]["host"] = data.host_name;
-                                                        service_dict[data.service_name]["status"] = data.status;
+                                                        service_dict[data.service_name]["type"] = data.protocol;
                                                     } else {
                                                         service_dict[data.service_name] = {
-                                                            "name":data.service_name,
-                                                            "type":"",
-                                                            "device":host.name,
-                                                            "device_group":host.device_group,
-                                                            "host":data.host_name,
-                                                            "status":data.status
+                                                            "name": data.service_name,
+                                                            "type": data.protocol,
+                                                            "device": host.name,
+                                                            "device_group": host.device_group,
+                                                            "host": "",
+                                                            "status": ""
                                                         };
                                                     }
-                                                }
+                                                    if (service_done && vhost_done) {
+                                                        tableViewModel.sslDataList.push(service_dict[data.service_name]);
+                                                    }
+                                                });
                                             });
-                                            if (service_done && vhost_done) {
-                                                var arr = [];
-                                                for (var each in service_dict) {
-                                                    arr.push(service_dict[each]);
+                                        sslMonitoringService
+                                            .getVhostList(host.id)
+                                            .then(function (res) {
+                                                vhost_done = true;
+                                                if (service_done && vhost_done) {
+                                                    tableViewModel.all_loadings[host.name] = true;
                                                 }
+                                                _.each(res, function (data) {
+                                                    if (data.service_name) {
+                                                        if (data.service_name in service_dict) {
+                                                            service_dict[data.service_name]["host"] = data.host_name;
+                                                            service_dict[data.service_name]["status"] = data.status;
+                                                        } else {
+                                                            service_dict[data.service_name] = {
+                                                                "name": data.service_name,
+                                                                "type": "",
+                                                                "device": host.name,
+                                                                "device_group": host.device_group,
+                                                                "host": data.host_name,
+                                                                "status": data.status
+                                                            };
+                                                        }
+                                                    }
+                                                });
+                                                if (service_done && vhost_done) {
+                                                    var arr = [];
+                                                    for (var each in service_dict) {
+                                                        arr.push(service_dict[each]);
+                                                    }
 
-                                                tableViewModel.sslDataList = tableViewModel.sslDataList.concat(arr);                                            }
-                                        });
-                                } else {
-                                    tableViewModel.all_loadings[host.name] = true;
-                                }
-                            });
+                                                    tableViewModel.sslDataList = tableViewModel.sslDataList.concat(arr);
+                                                }
+                                            });
+                                    } else {
+                                        tableViewModel.all_loadings[host.name] = true;
+                                    }
+                                });
+                            }
+                        } catch (e) {
+                            console.log('500 - Internal server error.');
+                            alert('500 - Internal server error. Failed to fetch device group mapping info.');
                         }
-                    }); 
+                        }
+                    });
             }
             getServiceList();
             tableViewModel.refresh = function() {
@@ -158,7 +173,7 @@
         'modalData',
         function ($scope, $rootScope, $state, $stateParams, $uibModal, $filter, $uibModalInstance, sslMonitoringService, modalData) {
               var modalViewModel = this;
-  
+
               modalViewModel.service_name = modalData.name;
               modalViewModel.device = modalData.device;
               modalViewModel.type = modalData.type;
@@ -183,7 +198,7 @@
                         _.each(res, function(data) {
                             if (vhost_list.indexOf(data.host_name) == -1) {
                                 vhost_list.push(data.host_name);
-                            } 
+                            }
                             if (!modalViewModel.vhost_dict[data.host_name]) {
                                 modalViewModel.vhost_dict[data.host_name] = []
                             }
@@ -285,7 +300,7 @@
                             });
                     }
                   }
-                  
+
               };
           }
       ])
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/cm/lib/postgres_db.py
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/cm/lib/postgres_db.py	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/cm/lib/postgres_db.py	(working copy)
@@ -1,25 +1,24 @@
-#python sqlite
-#Author : zhangjw
-#Create : 2016-02-22
-#Version: 1.0
-#DB-API interface for SQLite databases
+# python sqlite
+# Author : zhangjw
+# Create : 2016-02-22
+# Version: 1.0
+# DB-API interface for SQLite databases
 
 import psycopg2
-import os
-import json
+
 
 class DB(object):
     def __init__(self, conn):
         self.conn = conn
-        #Enabling Foreign Key Support
-        #cu = self.conn.cursor()
-        #cu.execute('PRAGMA foreign_keys = ON;')
-        #self.conn.commit()
-        #cu.close()
+        # Enabling Foreign Key Support
+        # cu = self.conn.cursor()
+        # cu.execute('PRAGMA foreign_keys = ON;')
+        # self.conn.commit()
+        # cu.close()
 
     @classmethod
     def get_connected_db(cls, path=None):
-        #conn = psycopg2.connect(database="cm", user="postgres", password="", host="10.23.0.142", port="5432")
+        # conn = psycopg2.connect(database="cm", user="postgres", password="", host="10.23.0.142", port="5432")
         conn = psycopg2.connect(database="cm",
                                 user="postgres",
                                 password="",
@@ -83,7 +82,7 @@
             self.conn.commit()
         cu.close()
 
-    #following functions just be called when CM package being install or be called to create data for testing
+    # following functions just be called when CM package being installed or be called to create data for testing
     # def create_table_device(self):
     #     print('Creating table device...')
     #     create_table_sql = '''CREATE TABLE IF NOT EXISTS `device` (
@@ -152,7 +151,7 @@
                             extend jsonb
                         )'''
         self.execute_sql(create_table_sql)
-        #FOREIGN KEY (device_id) REFERENCES device(id) ON DELETE CASCADE
+        # FOREIGN KEY (device_id) REFERENCES device(id) ON DELETE CASCADE
 
     def create_table_update(self):
         print('Creating table update_list...')
@@ -240,9 +239,11 @@
 
     def create_table_device_group(self):
         print('Creating table device_group...')
-        create_table_sql = ''' CREATE TABLE IF NOT EXISTS device_group(
-                                name varchar(64) NOT NULL primary key
-        ) '''
+        create_table_sql = '''
+        CREATE TABLE IF NOT EXISTS device_group (
+            name character varying(128) COLLATE pg_catalog."default" NOT NULL,
+            CONSTRAINT device_group_pkey PRIMARY KEY (name)
+        )'''
         self.execute_sql(create_table_sql)
 
     def create_table_ha_cluster(self):
@@ -300,7 +301,9 @@
                             comment text,
                             FOREIGN KEY (type) REFERENCES file_type(name) ON DELETE CASCADE,
                             extend jsonb
-        )'''
+        );
+        ALTER TABLE file_list ADD COLUMN IF NOT EXISTS device_id varchar(64); 
+        '''
         self.execute_sql(create_table_sql)
 
     def create_table_tar_file(self):
@@ -427,6 +430,12 @@
                               auth varchar(8192) DEFAULT NULL
                             );
                             ALTER TABLE user_authorization ADD COLUMN IF NOT EXISTS root INTEGER DEFAULT 0;
+                            ALTER TABLE user_authorization ADD COLUMN IF NOT EXISTS role_id INTEGER;
+                            ALTER TABLE user_authorization ADD COLUMN IF NOT EXISTS user_type varchar(32);
+                            ALTER TABLE user_authorization DROP CONSTRAINT IF EXISTS role_foreign_key;
+                            ALTER TABLE user_authorization ADD CONSTRAINT role_foreign_key FOREIGN KEY 
+                            (role_id) REFERENCES role (id);
+                            UPDATE user_authorization set user_type='Super Admin' where id=1;
                             '''
         self.execute_sql(create_table_sql)
 
@@ -460,7 +469,7 @@
                             level INTEGER default 2
         )'''
         self.execute_sql(create_table_sql)
-    
+
     def create_log_host_table(self):
         print('Creating table log_host...')
         # protocol: 0 - TCP, 1 - UDP
@@ -472,6 +481,32 @@
         )'''
         self.execute_sql(create_table_sql)
 
+    def create_table_role(self):
+        print('Creating role table...')
+        create_table_query = '''
+        CREATE TABLE IF NOT EXISTS role(
+        id integer NOT NULL GENERATED ALWAYS AS IDENTITY ( INCREMENT 1 START 1 MINVALUE 1 MAXVALUE 2147483647 CACHE 1 ),
+        role_name varchar(128),
+        created_at timestamp without time zone,
+        CONSTRAINT role_primary_key PRIMARY KEY (id)
+        )
+        '''
+        self.execute_sql(create_table_query)
+
+    def create_table_role_device_group(self):
+        print('Creating role_device_group table...')
+        create_table_query = '''
+        CREATE TABLE IF NOT EXISTS role_device_group (
+            id serial primary key,
+            role_id integer,
+            device_group_name varchar(128),
+            created_at timestamp without time zone,
+            FOREIGN KEY (role_id) REFERENCES role (id) ON DELETE CASCADE,
+            FOREIGN KEY (device_group_name) REFERENCES device_group(name) ON DELETE CASCADE
+        );'''
+        self.execute_sql(create_table_query)
+
+
 if __name__ == '__main__':
     db = DB.get_connected_db()
     db.create_table_cm_role()
@@ -493,6 +528,7 @@
     db.create_table_file()
     db.create_table_audit_user()
     db.create_table_extension_log()
+    db.create_table_role()
     db.create_table_user_authorization()
     db.create_table_operation_log()
     db.create_table_schedule_backup_all()
@@ -500,4 +536,5 @@
     db.create_log_host_table()
     db.create_table_config_template()
     db.create_table_device_config_template()
+    db.create_table_role_device_group()
     db.close()
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/cm/lib/task_scheduler.py
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/cm/lib/task_scheduler.py	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/cm/lib/task_scheduler.py	(working copy)
@@ -743,7 +743,7 @@
 
         create_time = datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S')
         db = DB.get_connected_db()
-        insert_sql = "INSERT INTO file_list(name, create_time, modify_time, type, device_type) values('%s', '%s', '%s', '%s', '%s') on conflict (name) do update set modify_time=excluded.modify_time" % (file_name, create_time, create_time, 'device', device_info[0]['type'])
+        insert_sql = "INSERT INTO file_list(name, create_time, modify_time, type, device_type, device_id) values('%s', '%s', '%s', '%s', '%s', '%s') on conflict (name) do update set modify_time=excluded.modify_time" % (file_name, create_time, create_time, 'device', device_info[0]['type'], device_info[0]['id'])
         #delete_sql = "DELETE FROM file_list where name='%s' " % file_name
         db = DB.get_connected_db()
         #db.execute_sql(delete_sql)
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/cm/models/device_mgmt/device/__init__.py
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/cm/models/device_mgmt/device/__init__.py	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/cm/models/device_mgmt/device/__init__.py	(working copy)
@@ -578,7 +578,7 @@
             save_sql = "INSERT INTO device(id, zone, name, ip_address, protocol, restapi_port, restapi_username, restapi_password, console_username, console_password, connection, status, license_key, gateway_domain, location, firewall_ip, intranet_ip, version, type, own, log_enable, webui_port, device_group, enable_password) Values " + "('%(id)s', '%(zone)s', '%(name)s', '%(ip)s', '%(protocol)s', '%(restapi_port)s', '%(restapi_username)s', '%(restapi_password)s', '%(console_username)s', '%(console_password)s', 'connected', '%(status)s', '%(license_key)s', '%(gateway_domain)s', '%(location)s', '%(firewall_ip)s', '%(intranet_ip)s', '%(version)s', '%(type)s', '%(own)s', '%(log_enable)d', '%(webui_port)d', '%(device_group)s', '%(enable_password)s')"%data
             db.execute_sql(save_sql)
             create_time = datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S')
-            insert_config_sql = "INSERT INTO file_list(name, create_time, modify_time, type, comment, device_type) values('%s', '%s', '%s', '%s', '%s', '%s')" % (data['name'], create_time, data['name'], 'device', '', data['type'])
+            insert_config_sql = "INSERT INTO file_list(name, create_time, modify_time, type, comment, device_type, device_id) values('%s', '%s', '%s', '%s', '%s', '%s', '%s')" % (data['name'], create_time, create_time, 'device', '', data['type'], data['id'])
             db.execute_sql(insert_config_sql)
             db.close()
 
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/cm/models/device_mgmt/device_group/__init__.py
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/cm/models/device_mgmt/device_group/__init__.py	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/cm/models/device_mgmt/device_group/__init__.py	(working copy)
@@ -1,17 +1,23 @@
-from hive.imports.model import *
+import datetime
+import json
+import os
+import time
+
+from cm.lib.communication import L
+from cm.lib.parse_configfile import DEFAULT_CONFIG_FILE_PATH, DEFAULT_VSITE_PATH
 from cm.lib.postgres_db import DB
 from django.utils.translation import ugettext_lazy as _
 from djproject.an_settings import *
-from hive.utils import andebug
-from cm.lib.communication import L
-from cm.lib.parse_configfile import DEFAULT_CONFIG_FILE_PATH, DEFAULT_VSITE_PATH
-import shutil, os
-__=_
+from hive.imports.model import *
+
+__ = _
+
 
 class DeviceGroup(ANModel):
     name = CharField(verbose_name='Device Group Name', primary_key=True, length='1..64')
     managed_devices_info = FieldGroup(writable=False, verbose_name='Managed Devices', level=BASIC, fields={
-        'device_list': AssoField2(verbose_name='Managed Devices', tgt='device_mgmt.device.Device.device_group', mul='1', pos='left', optional=True),
+        'device_list': AssoField2(verbose_name='Managed Devices', tgt='device_mgmt.device.Device.device_group', mul='1',
+                                  pos='left', optional=True),
     })
 
     class Meta:
@@ -30,7 +36,6 @@
                 self._model._meta.mark_delay_query(each)
             return QuerySet(self._model, result)
 
-
         def _insert(self, instance):
             data = instance.get_field_dict()
 
@@ -42,8 +47,8 @@
             for each in zone_data:
                 if each[0] == data["name"]:
                     raise ModelQueryException(CLICmdError(__('This device_group name has been imported.')))
-            
-            save_sql = "INSERT INTO device_group(name) values " + "('%(name)s')"%data
+
+            save_sql = "INSERT INTO device_group(name) values " + "('%(name)s')" % data
             db = DB.get_connected_db()
             db.execute_sql(save_sql)
             db.close()
@@ -68,13 +73,15 @@
                 if not old_id_list:
                     raise ModelQueryException(CLICmdError(__('Please select device.')))
                 else:
-                    raise ModelQueryException(CLICmdError(__('Device must has one device group. Can not unbind device with device group.')))
+                    raise ModelQueryException(
+                        CLICmdError(__('Device must has one device group. Can not unbind device with device group.')))
 
             if not set(old_id_list).issubset(new_ip_list):
                 raise ModelQueryException(CLICmdError(__('Can not unbind device with device group.')))
 
             for device in device_list:
-                update_sql = "UPDATE device SET device_group = '%s' WHERE ip_address = '%s'" % (instance.name, device['ip'])
+                update_sql = "UPDATE device SET device_group = '%s' WHERE ip_address = '%s'" % (
+                    instance.name, device['ip'])
                 db.execute_sql(update_sql)
             db.close()
             mark_expire_all(get_model('cm', ['device_mgmt', 'device', 'Device']))
@@ -82,21 +89,36 @@
 
         def _delete(self, pk_list):
             db = DB.get_connected_db()
+            # Check role whether the device group is active
+            for each_pk in pk_list:
+                group_name = each_pk['name']
+                select_sql = '''
+                    select id, role_id from role_device_group where device_group_name = '%s'
+                ''' % group_name
+                select_data = db.fetchall(select_sql)
+                key = ['id', 'role_id']
+                select_result = [dict(zip(key, each)) for each in select_data]
+                if len(select_result) > 0:
+                    raise ModelQueryException(
+                        CLICmdError(__("An active device group cannot be deleted. "
+                                       "Please unbind the device group from the role.")))
+
             for each_pk in pk_list:
                 group_name = each_pk['name']
                 fetch_device_sql = "SELECT id, name, ip_address FROM device WHERE device_group = '%s'" % group_name
                 device_data = db.fetchall(fetch_device_sql)
                 key = ['id', 'name', 'ip']
                 device_result = [dict(zip(key, each)) for each in device_data]
-                
+
                 for each_device in device_result:
-                    select_sql = 'SELECT name, state, device_list from task;' 
+                    select_sql = 'SELECT name, state, device_list from task;'
                     select_data = db.fetchall(select_sql)
                     key = ['name', 'state', 'device_list']
                     result = [dict(zip(key, each)) for each in select_data]
 
-                    #get backup file list
-                    select_sql = "SELECT name, device_type FROM file_list WHERE type='backup' and modify_time='%s'" % each_device['name']
+                    # get backup file list
+                    select_sql = "SELECT name, device_type FROM file_list WHERE type='backup' and modify_time='%s'" % \
+                                 each_device['name']
                     select_data = db.fetchall(select_sql)
                     key = ['name', 'device_type']
                     backup_result = [dict(zip(key, each)) for each in select_data]
@@ -105,12 +127,12 @@
                     db.execute_sql(delete_sql)
 
                     L.remove_lock(each_device['ip'])
-                    
-                    #delete from file_list, delete device item and backup item
+
+                    # delete from file_list, delete device item and backup item
                     delete_sql = "DELETE FROM file_list WHERE modify_time= '%s'" % each_device['name']
                     db.execute_sql(delete_sql)
 
-                    #remove the backup config file
+                    # remove the backup config file
                     for item in backup_result:
                         backup_path = DEFAULT_CONFIG_FILE_PATH + 'backup/' + item['name']
                         if os.path.exists(backup_path):
@@ -119,7 +141,7 @@
                                 # need to remove both .all_cfg_tar file and dir path
                                 os.popen("rm -rf %s" % backup_path[0:-12]).read()
 
-                    #delete vsite from vsite_list
+                    # delete vsite from vsite_list
                     select_sql = "SELECT vs_name FROM vsite_list WHERE device_name='%s'" % each_device['name']
                     select_data = db.fetchall(select_sql)
                     key = ['vs_name']
@@ -127,13 +149,13 @@
 
                     delete_sql = "DELETE FROM vsite_list WHERE device_name='%s'" % each_device['name']
                     db.execute_sql(delete_sql)
-                    
-                    #remove the vsite config file
+
+                    # remove the vsite config file
                     for item in result:
                         vsite_path = DEFAULT_VSITE_PATH + each_device['name'] + '-' + item['vs_name']
                         if os.path.exists(vsite_path):
                             os.remove(vsite_path)
-                    #remove the device config file
+                    # remove the device config file
                     file_path = DEFAULT_CONFIG_FILE_PATH + 'device/' + each_device['name']
                     if os.path.exists(file_path):
                         os.remove(file_path)
@@ -146,3 +168,165 @@
             db.close()
             mark_expire_all(get_model('cm', ['device_mgmt', 'device', 'Device']))
             return
+
+
+class RoleDeviceGroup(ANModel):
+    default = FieldGroup(verbose_name=_('Role-Based Device Management Settings'), fields={
+        'role_id': CharField(verbose_name=_('Role Id'), primary_key=True, optional=True),
+        'device_group_name': CharField(verbose_name=_('Device Group Name'), optional=True),
+    })
+
+    class FilterRoleDeviceGroups(Action):
+        verbose_name = _('Filter Role Device Groups')
+        action_name = _('FilterRoleDeviceGroups')
+        option_fields = (
+            CharField(name='role_id', verbose_name='Role Id'),
+        )
+
+    class UpdateRoleDeviceGroups(Action):
+        verbose_name = _('Update Role Device Groups')
+        action_name = _('UpdateRoleDeviceGroups')
+        option_fields = (
+            CharField(name='role_id', verbose_name='Role Id'),
+        )
+
+    class Meta():
+        verbose_name = 'Role-Based Device Management'
+
+    class Manager(CLIManager):
+
+        def _perform_FilterRoleDeviceGroups(self, options):
+            role_id = int(options.get('role_id', '0'))
+            db = DB.get_connected_db()
+            fetchall_sql = '''
+                SELECT name FROM device_group
+            '''
+            if role_id != 0:
+                fetchall_sql = '''select device_group_name as name from role_device_group where role_id=%d;''' % role_id
+            device_group_data = db.fetchall(fetchall_sql)
+
+            device_group_key = ['name']
+            device_group_result = [dict(zip(device_group_key, each)) for each in device_group_data]
+
+            fetch_device_sql = '''
+                SELECT id, zone, name, ip_address, protocol, restapi_port, restapi_username, restapi_password,
+                console_username, console_password, connection, status, version, license_key, gateway_domain, location,
+                firewall_ip, intranet_ip, type, extend_fields, own, log_enable, snmp_general, webui_port, device_group,
+                enable_password, extend FROM device order by create_time
+            '''
+            device_list_data = db.fetchall(fetch_device_sql)
+            db.close()
+            device_list_key = ['id', 'zone', 'name', 'ip', 'protocol', 'restapi_port', 'restapi_username',
+                               'restapi_password',
+                               'console_username', 'console_password', 'connection', 'status', 'version', 'license_key',
+                               'gateway_domain', 'location', 'firewall_ip', 'intranet_ip', 'type', 'extend_fields',
+                               'own',
+                               'log_enable', 'snmp_general', 'webui_port', 'device_group', 'enable_password', 'extend']
+            device_list_result = [dict(zip(device_list_key, each)) for each in device_list_data]
+
+            role_device_list = []
+            for each_group in device_group_result:
+                device_list = []
+                for each_device in device_list_result:
+                    if each_group["name"] == each_device['device_group']:
+                        del each_device['extend']
+                        each_device["backup_enable"] = False
+                        each_device['device_group'] = each_device['device_group']
+                        each_device['restapi_account'] = {'restapi_username': each_device['restapi_username'],
+                                                          'restapi_password': None}
+                        del each_device['restapi_username']
+                        del each_device['restapi_password']
+                        each_device['console_account'] = {'console_username': each_device['console_username'],
+                                                          'console_password': None}
+                        del each_device['console_username']
+                        del each_device['console_password']
+                        if each_device['connection'] == 'connected':
+                            each_device['connection'] = True
+                        else:
+                            each_device['connection'] = False
+                        if each_device['status'] == 'active':
+                            each_device['status'] = True
+                        else:
+                            each_device['status'] = False
+                        if each_device['license_key'] == 'None':
+                            each_device['license_key'] = ''
+                        if each_device['version']:
+                            replace_result = each_device['version'].replace('\\n', '\n')
+                            rtn = cli_parse(replace_result, [
+                                RegexParser('Host name : (.+?)\n', MATCHONE),
+                                RegexParser('System CPU : (.+?)\n', MATCHONE),
+                                RegexParser('System RAM : (.+?)\n', MATCHONE),
+                                RegexParser('System boot time : (.+?)\n', MATCHONE),
+                                RegexParser('System up time : (.+?)\n', MATCHONE),
+                                RegexParser('Platform Bld Date : (.+?)\n', MATCHONE),
+                                RegexParser('SSL HW : (.+?)\n', MATCHONE),
+                                RegexParser('Compression HW : (.+?)\n', MATCHONE),
+                                RegexParser('Network Interface : (.+?)\n', MATCHONE),
+                                RegexParser('Model : (.+?)\n', MATCHONE),
+                                RegexParser('Serial Number : (.+?)\n', MATCHONE),
+                                RegexParser('([ArrayOS|InfosecOS].+?)\n', MATCHONE),
+                                RegexParser('Licensed Limits : (.+?)\n', MATCHONE),
+                                RegexParser('Licensed Features : (.*)', MATCHONE, reflags=re.S),
+                                RegexParser('License Date : (.*?)\n', MATCHONE),
+                            ])
+                            each_device['host_name'] = rtn[0][0] if rtn[0] else ''
+                            each_device['system_cpu'] = rtn[1][0] if rtn[1] else ''
+                            each_device['system_ram'] = rtn[2][0] if rtn[2] else ''
+                            each_device['system_boot_time'] = rtn[3][0] if rtn[3] else ''
+                            each_device['system_up_time'] = rtn[4][0] if rtn[4] else ''
+                            each_device['platform_bld_date'] = rtn[5][0] if rtn[5] else ''
+                            each_device['ssl_hw'] = rtn[6][0] if rtn[6] else ''
+                            each_device['compression_hw'] = rtn[7][0] if rtn[7] else ''
+                            each_device['network_interface'] = rtn[8][0] if rtn[8] else ''
+                            each_device['model'] = rtn[9][0].split(',')[0] if rtn[9] else ''
+                            each_device['serial_number'] = rtn[10][0] if rtn[10] else ''
+                            each_device['build_version'] = rtn[11][0] if rtn[11] else ''
+                            each_device['license_limit'] = rtn[12][0] if rtn[12] else ''
+                            each_device['license_date'] = rtn[-1][0] if rtn[-1] else ''
+                            each_device['license_feature'] = re.sub("\s+", ", ",
+                                                                    rtn[-2][0].split('License Key')[0]).strip(
+                                ', ') if \
+                                rtn[-2] else ''
+                        del each_device['version']
+
+                        if each_device['snmp_general']:
+                            tmp_obj = {}
+                            obj = json.loads(each_device['snmp_general'])
+                            tmp_obj["snmp_enable"] = obj["snmp_enable"] if "snmp_enable" in obj else False
+                            tmp_obj["community"] = obj["community"] if "community" in obj else ""
+                            each_device['snmp_general'] = tmp_obj
+
+                        if each_device['type'].lower() in ADC_TYPE_LIST + WAF_TYPE_LIST and each_device['license_key']:
+                            license_date = each_device['license_key'].split('-')[-1]
+                            try:
+                                if len(license_date) > 8:
+                                    license_date = license_date[2:]
+                                each_device['license_date'] = "Expires on " + time.strftime("%b %d %G",
+                                                                                            time.strptime(license_date,
+                                                                                                          "%Y%m%d"))
+                            except Exception, e:
+                                each_device['license_date'] = "Permanent"
+                        each_device['group_name_from'] = ''
+                        device_list.append(each_device)
+                role_device_list.append({
+                    "group_name": each_group["name"],
+                    "device_list": device_list
+                })
+            return {"result": role_device_list}
+
+        def _perform_UpdateRoleDeviceGroups(self, options):
+            data = options
+            db = DB.get_connected_db()
+
+            # Remove the existing role-device-group mapping before updating the relationship.
+            delete_sql = "delete from role_device_group where role_id=%d" % data['role_id']
+            delete_response = db.execute_sql(delete_sql)
+
+            created_at = datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S')
+            for group_name in data["groups"]:
+                insert_config_sql = ('''
+                INSERT INTO role_device_group(role_id, device_group_name, created_at) values(%d, '%s', '%s')
+                ''' % (data['role_id'], group_name, created_at))
+                db.execute_sql(insert_config_sql)
+            db.close()
+            return {"result": None}
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/cm/models/system/user_mgmt/__init__.py
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/cm/models/system/user_mgmt/__init__.py	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/cm/models/system/user_mgmt/__init__.py	(working copy)
@@ -1,26 +1,35 @@
-from hive.imports.model import *
-from django.utils.translation import ugettext_lazy as _
+import datetime
+import json
+
 from cm.lib.postgres_db import DB
-__=_
+from django.utils.translation import ugettext_lazy as _
+from hive.imports.model import *
+
+__ = _
+
 
 class Administrator(ANModel):
     default = FieldGroup(editable=False, fields={
         'username': CharField(primary_key=True, length='1..16'),
         'passwords': PasswordField(length='1..128', editable=True),
-        'email':CharField(length='1..128', optional=True, editable=True),
-        'phone_num':CharField(length='1..128', optional=True, editable=True),
+        'email': CharField(length='1..128', optional=True, editable=True),
+        'phone_num': CharField(length='1..128', optional=True, editable=True),
         'level': EnumField(verbose_name=_('User Level'), default='config', values=(
-                           ('enable', 'Enable', ''),
-                           ('config', 'Config', ''),
-                           ), editable=True),
+            ('enable', 'Enable', ''),
+            ('config', 'Config', ''),
+        ), editable=True),
+        'user_type': CharField(verbose_name='User Type', optional=True),
+        'role_id': IntegerField(verbose_name='Role Id', optional=True),
+        'role_name': CharField(length='1..16', optional=True),
         'root': BooleanField(verbose_name=_('Root'), default=False)
     })
+
     class Meta:
         verbose_name = _('System Administrator')
-        list_config_options={'columns':[
-            {'name':'username'},
-            {'name':'level'},
-            ]}
+        list_config_options = {'columns': [
+            {'name': 'username'},
+            {'name': 'level'},
+        ]}
         show_im_export_button = True
 
     class Manager(CLIManager):
@@ -31,7 +40,20 @@
             for item_name in result_name:
                 model = get_model('cm', ['system', 'user_mgmt', 'UserAuthorization'])
                 manager = model.get_manager(self._session)
-                item_name['root'] = manager.get({'username': item_name['username']}).get_field_dict()['root']
+                if 'user_type' not in item_name:
+                    item_name['user_type'] = "Common Admin"
+                if 'role_id' not in item_name:
+                    item_name['role_id'] = 0
+                if 'role_name' not in item_name:
+                    item_name['role_name'] = ""
+                user_auth_entry = manager.get({'username': item_name['username']}).get_field_dict()
+                item_name['root'] = user_auth_entry['root']
+                if 'user_type' in user_auth_entry and user_auth_entry['user_type'] is not None:
+                    item_name['user_type'] = user_auth_entry['user_type']
+                if 'role_id' in user_auth_entry and user_auth_entry['role_id'] is not None:
+                    item_name['role_id'] = user_auth_entry['role_id']
+                if 'role_name' in user_auth_entry and user_auth_entry['role_name'] is not None:
+                    item_name['role_name'] = user_auth_entry['role_name']
                 for item_info in result_info:
                     if item_info['username'] == item_name['username']:
                         item_name.update(item_info)
@@ -39,7 +61,6 @@
                             item_name['email'] = ""
                         if 'phone_num' not in item_name:
                             item_name['phone_num'] = ""
-
             for data in result_name:
                 self._model._meta.mark_delay_query(data)
             return QuerySet(self._model, result_name)
@@ -49,7 +70,7 @@
             session = self._session
             model = get_model('cm', ['system', 'user_mgmt', 'UserAuthorization'])
             manager = model.get_manager(self._session)
-            #should judge whether a common user want to create a root user.
+            # should judge whether a common user want to create a root user.
             root = manager.get({'username': session.username}).get_field_dict()['root']
             if not root:
                 raise ModelQueryException(CLICmdError(__('You are common admin user, can not create users!')))
@@ -57,20 +78,22 @@
             if len(data["phone_num"]) > 128:
                 raise ModelQueryException(CLICmdError(__("Invalid phone number.")))
             result = self.cli.cmd('user name "%(username)s" "%(passwords)s" "%(level)s"' % data,
-                                BlankParser(nonblank_exception=CLICmdError, supplement=True))
+                                  BlankParser(nonblank_exception=CLICmdError, supplement=True))
             result = self.cli.cmd('user info "%(username)s" "%(email)s" "%(phone_num)s"' % data,
-                                BlankParser(nonblank_exception=CLICmdError, supplement=True))
-            manager.insert(model(**{"username": data['username'], "root":data["root"]}))
+                                  BlankParser(nonblank_exception=CLICmdError, supplement=True))
+            manager.insert(model(**{"username": data['username'], "root": data["root"],
+                                    "user_type": data["user_type"], "role_id": data["role_id"]}))
             return result
-            
+
         def _update(self, instance):
             data = instance.get_field_dict()
             session = self._session
             model = get_model('cm', ['system', 'user_mgmt', 'UserAuthorization'])
             manager = model.get_manager(session)
-            #should judge whether a common user want to edit a root user.
+            # should judge whether a common user want to edit a root user.
             root = manager.get({'username': session.username}).get_field_dict()['root']
             auth = manager.get({'username': data['username']}).get_field_dict()['auth']
+            user_type = manager.get({'username': data['username']}).get_field_dict()['user_type']
             if not root:
                 if data['username'] != session.username:
                     raise ModelQueryException(CLICmdError(__('You are common admin user, can not edit other users!')))
@@ -78,67 +101,83 @@
             if len(data["phone_num"]) > 128:
                 raise ModelQueryException(CLICmdError(__("Invalid phone number.")))
             result = self.cli.cmd('user name "%(username)s" "%(passwords)s" "%(level)s"\nYES\n' % data,
-                                  RegexParser('change user password and level', MATCHONE)) # ignore the output
+                                  RegexParser('change user password and level', MATCHONE))  # ignore the output
             if data["email"] and data["phone_num"]:
                 result = self.cli.cmd('user info "%(username)s" "%(email)s" "%(phone_num)s"' % data,
                                       BlankParser(nonblank_exception=CLICmdError, supplement=True))
-            manager.update(model(**{"username": data['username'], "root":data["root"], "auth": auth}))
+            manager.update(model(**{"username": data['username'], "root": data["root"], "auth": auth,
+                                    "user_type": user_type, "role_id": data["role_id"]}))
             return result
-        
+
         def _delete(self, pk_list):
             session = self._session
             model = get_model('cm', ['system', 'user_mgmt', 'UserAuthorization'])
             manager = model.get_manager(session)
             root = manager.get({'username': session.username}).get_field_dict()['root']
-            #should judge whether a common user want to delete user.
+            # should judge whether a common user want to delete user.
             if not root:
                 raise ModelQueryException(CLICmdError(__('You are common admin user, can not delete users!')))
-            #should judge whether a root user want to commit suicide
+            # should judge whether a root user want to commit suicide
             username_list = [each['username'] for each in pk_list]
             if session.username in username_list:
                 raise ModelQueryException(CLICmdError(__('You can not delete yourself!')))
             self.cli.set_config()
-            #db = DB.get_connected_db()
-            for each in pk_list:     
+            # db = DB.get_connected_db()
+            for each in pk_list:
                 result = self.cli.cmd('no user "%s"' % each['username'],
-                                    BlankParser(nonblank_exception=CLICmdError, supplement=True))
+                                      BlankParser(nonblank_exception=CLICmdError, supplement=True))
                 # should not delete auth info here, avoid not write memory and reboot, will do clean in script when bootup
-                # delete_sql = ''' DELETE FROM user_authorization WHERE username='%s' ''' % each['username']
-                # db.execute_sql(delete_sql)
-            #db.close()
+                delete_sql = ''' DELETE FROM user_authorization WHERE username='%s' ''' % each['username']
+                db.execute_sql(delete_sql)
+            db.close()
             return
 
+
 class UserAuthorization(ANModel):
     default = FieldGroup(editable=False, fields={
         'username': CharField(primary_key=True, length='1..16'),
         'auth': JSONField(verbose_name='Authorization', optional=True),
+        'user_type': CharField(verbose_name='User Type', optional=True),
+        'role_id': IntegerField(verbose_name='Role Id', optional=True),
+        'role_name': CharField(length='1..16', optional=True),
         'root': BooleanField(verbose_name=_('Root'), default=False)
     })
+
     class Meta:
         verbose_name = _('User Authorization')
-        list_config_options={'columns':[
-            {'name':'username'},
-            {'name':'auth'},
-            ]}
+        list_config_options = {'columns': [
+            {'name': 'username'},
+            {'name': 'auth'},
+        ]}
         show_im_export_button = True
 
+    class GetRoleByUsername(Action):
+        verbose_name = _('Get Role By Username')
+        action_name = _('GetRoleByUsername')
+
     class Manager(CLIManager):
         def _get(self, pk_dict=None):
             db = DB.get_connected_db()
-            fetchone_sql = ''' SELECT username, auth, root FROM user_authorization WHERE username='%s' ''' % pk_dict.get('username', '')
-            data = db.fetchone(fetchone_sql)
+            get_users_query = '''
+                            select ua.username, ua.auth, ua.root, ua.user_type, ua.role_id, r.role_name from "user_authorization" ua
+                            left join "role" r on r.id = ua.role_id where ua.username = '%s';
+            ''' % (pk_dict.get('username', ''))
+            data = db.fetchone(get_users_query)
             if data:
-                return self._model(**dict(zip(['username', 'auth', 'root'], data)))
+                return self._model(**dict(zip(['username', 'auth', 'root', 'user_type', 'role_id', 'role_name'], data)))
             else:
-                # the authorization info not found in the table, return a empty auth string
+                # the authorization info not found in the table, return an empty auth string
                 return self._model(username=pk_dict.get('username', ''), auth='', root=False)
 
         def _get_query_set(self):
             db = DB.get_connected_db()
-            select_sql = "SELECT username, auth, root FROM user_authorization;"
+            select_sql = '''
+                        select ua.username, ua.auth, ua.root, ua.user_type, ua.role_id, r.role_name from
+                        "user_authorization" ua left join "role" r on r.id = ua.role_id;
+            '''
             data = db.fetchall(select_sql)
             db.close()
-            key = ['username', 'auth', 'root']
+            key = ['username', 'auth', 'root', 'user_type', 'role_id', 'role_name']
             result = [dict(zip(key, each)) for each in data]
             return QuerySet(self._model, result)
 
@@ -158,18 +197,27 @@
         #     # db.execute_sql(insert_sql)
         #     # db.close()
         #     # return
-            
+
         def _update(self, instance):
             db = DB.get_connected_db()
-            username = instance.username
             root = 1 if instance.root else 0
+            if not instance.auth and instance.user_type == 'Device Admin':
+                instance.auth = '''{"ssl_monitoring":{"access":true},"ha":{"access":false,"ha_cluster":{"access":false},"ha_monitoring":{"access":false}},"image":{"access":true,"add":false,"system_update":true,"delete":false},"system":{"task":{"access":false,"delete":false},"extension":{"enable":false,"update":false,"access":false,"disable":false,"install":false,"uninstall":false},"admin":{"access":false,"delete_operation_log":false},"notification":{"access":false},"storage":{"access":false},"host":{"access":false}},"device":{"device":{"access":true,"add":false,"save":true,"delete":false},"device_group":{"access":true,"add":false,"delete":false}},"configuration":{"access":false},"topology":{"slb_topology":{"access":true,"disable_rs":true,"all_rs_block":false,"edit_rs_weight":true,"enable_rs":true}},"reporting":{"access":false},"alerting":{"access":false},"event":{"access":false},"auditing":{"log_analysis":{"access":true},"engine":{"access":false}},"virtualization":{"access":false},"vpn_mgmt":{"access":false}}'''
             if instance.auth == "all":
                 instance.auth = None
             if root == 1 or not instance.auth:
                 # common -> root
                 # root -> root
                 # allow all auth
-                update_sql = ''' INSERT INTO user_authorization(username, auth, root) VALUES('%s', NULL, %d) ON conflict(username) DO UPDATE SET "auth" = excluded.auth, "root" = excluded.root''' % (instance.username, root)
+                update_sql = '''
+                INSERT INTO user_authorization(username, auth, root, user_type, role_id) VALUES ('%s', NULL, %d, '%s', %d) 
+                ON conflict(username) DO UPDATE SET "auth" = excluded.auth, "root" = excluded.root
+                ''' % (instance.username, root, instance.user_type, instance.role_id)
+                if instance.role_id == 0:
+                    update_sql = '''
+                                    INSERT INTO user_authorization(username, auth, root, user_type, role_id) VALUES ('%s', NULL, %d, '%s', NULL)
+                                    ON conflict(username) DO UPDATE SET "auth" = excluded.auth, "root" = excluded.root
+                                    ''' % (instance.username, root, instance.user_type)
             else:
                 # root -> common
                 # common -> common
@@ -183,11 +231,19 @@
                     instance.auth = json.dumps(instance.auth)
                 else:
                     raise ModelQueryException(CLICmdError(__('User authentication information format error')))
-                update_sql = ''' INSERT INTO user_authorization(username, auth, root) VALUES('%s', '%s', %d) ON conflict(username) DO UPDATE SET "auth" = excluded.auth, "root" = excluded.root''' % (instance.username, instance.auth, root)
+                update_sql = ''' 
+                INSERT INTO user_authorization(username, auth, root, user_type, role_id) VALUES ('%s', '%s', %d, '%s', %d) 
+                ON conflict(username) DO UPDATE SET "auth" = excluded.auth, "root" = excluded.root
+                ''' % (instance.username, instance.auth, root, instance.user_type, instance.role_id)
+                if instance.role_id == 0:
+                    update_sql = '''
+                                    INSERT INTO user_authorization(username, auth, root, user_type, role_id) VALUES ('%s', '%s', %d, '%s', NULL)
+                                    ON conflict(username) DO UPDATE SET "auth" = excluded.auth, "root" = excluded.root
+                                    ''' % (instance.username, instance.auth, root, instance.user_type)
             db.execute_sql(update_sql)
             db.close()
             return
-        
+
         # def _delete_instance(self, instance):
         #     db = DB.get_connected_db()
         #     delete_sql = ''' DELETE FROM user_authorization WHERE username='%s' ''' % instance.username
@@ -195,4 +251,93 @@
         #     db.close()
         #     return
 
+        def _perform_GetRoleByUsername(self, options):
+            username = options.get('username', '')
+            db = DB.get_connected_db()
+            get_user_query = ''' select ua.username, ua.root, ua.user_type, ua.role_id, r.role_name from 
+            "user_authorization" ua left join role r on ua.role_id = r.id where ua.username = '%s'; ''' % username
+            data = db.fetchone(get_user_query)
+            db.close()
+            if data:
+                key = ['username', 'root', 'user_type', 'role_id']
+                result = dict(zip(key, data))
+                return {"result": result}
+            else:
+                return {"result": {'username': username, 'root': False, 'user_type': 'Common Admin', 'role_id': '0'}}
+
+
+class Role(ANModel):
+    default = FieldGroup(editable=True, fields={
+        'id': IntegerField(primary_key=True, verbose_name='Role Id'),
+        'role_name': CharField(verbose_name=_('Role Name'), length='1..64')
+    })
+
+    class Meta:
+        verbose_name = _('Role Management')
+        list_config_options = {'columns': [
+            {'name': 'id'},
+            {'name': 'role_name'},
+        ]}
+        show_im_export_button = False
+
+    class Manager(CLIManager):
+
+        def _get_query_set(self):
+            db = DB.get_connected_db()
+            select_sql = '''select id, role_name from role;'''
+            data = db.fetchall(select_sql)
+            db.close()
+            key = ['id', 'role_name']
+            result = [dict(zip(key, each)) for each in data]
+            return QuerySet(self._model, result)
+
+        def _insert(self, instance):
+            data = instance.get_field_dict()
+            db = DB.get_connected_db()
+
+            # Check role with same name already exists
+            select_sql = "select id from role where role_name='%s'" % data['role_name']
+            select_data = db.fetchall(select_sql)
+            key = ['id', 'role_name']
+            select_result = [dict(zip(key, each)) for each in select_data]
+            if len(select_result) > 0:
+                raise ModelQueryException(CLICmdError(__('Role Name has exists.')))
+            created_at = datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S')
+            insert_config_sql = ('''
+            INSERT INTO role(role_name, created_at) values('%s', '%s') 
+            ''' % (data['role_name'], created_at))
+            db.execute_sql(insert_config_sql)
+            db.close()
+
+        def _update(self, instance):
+            data = instance.get_field_dict()
+            db = DB.get_connected_db()
+
+            # Check role with same name already exists
+            select_sql = "select id from role where role_name='%s'" % data['role_name']
+            select_data = db.fetchall(select_sql)
+            key = ['id', 'role_name']
+            select_result = [dict(zip(key, each)) for each in select_data]
+            if len(select_result) > 0:
+                raise ModelQueryException(CLICmdError(__('Role Name has exists.')))
+            insert_config_sql = (''' UPDATE role SET role_name='%s' where id=%d;''' % (data['role_name'], data['id']))
+            db.execute_sql(insert_config_sql)
+            db.close()
+
+        def _delete_instance(self, instance):
+            db = DB.get_connected_db()
+            data = instance.get_field_dict()
+            # Check role whether the role is active
+            select_sql = "select id, role_id from user_authorization where role_id=%d" % instance.id
+            select_data = db.fetchall(select_sql)
+            key = ['id', 'role_id']
+            select_result = [dict(zip(key, each)) for each in select_data]
+            if len(select_result) > 0:
+                raise ModelQueryException(
+                    CLICmdError(__("An active role cannot be deleted. Please unbind the user's role.")))
+            delete_sql = ''' DELETE FROM role_device_group WHERE role_id=%d ''' % instance.id
+            db.execute_sql(delete_sql)
+            delete_sql = ''' DELETE FROM role WHERE id=%d ''' % instance.id
+            db.execute_sql(delete_sql)
+            db.close()
 
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/cm/router.py
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/cm/router.py	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/cm/router.py	(working copy)
@@ -751,12 +751,19 @@
         oper_log('info', 'system', 'Update version from repository successfully.')
         return HttpResponse(json.dumps({"state": True, "data": output}), content_type='application/json')
 
-def get_adc_ssl_cert(requset):
+
+def get_adc_ssl_cert(request):
+    role_id = int(json.loads(request.POST["data"])["role_id"])
     result = []
     cert_device_list = []
 
     db = DB.get_connected_db()
     fetchall_sql = "select name, ip_address, protocol, restapi_port, restapi_username, restapi_password, type, enable_password from device"
+    if role_id != 0:
+        fetchall_sql = '''
+            select name, ip_address, protocol, restapi_port, restapi_username, restapi_password, type, enable_password 
+            from device where device_group in (select device_group_name from role_device_group where role_id=%d);
+            ''' % role_id
     data = db.fetchall(fetchall_sql)
     if not data:
         return HttpResponse(json.dumps({"state": True, "data": result}), content_type='application/json')
@@ -843,12 +850,19 @@
 
     return HttpResponse(json.dumps({"state": True, "data": result}), content_type='application/json')
 
-def get_vpn_ssl_cert(requset):
+
+def get_vpn_ssl_cert(request):
+    role_id = int(json.loads(request.POST["data"])["role_id"])
     result = []
     cert_device_list = []
 
     db = DB.get_connected_db()
     fetchall_sql = "select name, ip_address, protocol, restapi_port, restapi_username, restapi_password, type, enable_password from device"
+    if role_id != 0:
+        fetchall_sql = '''
+            select name, ip_address, protocol, restapi_port, restapi_username, restapi_password, type, enable_password 
+            from device where device_group in (select device_group_name from role_device_group where role_id=%d);
+            ''' % role_id
     data = db.fetchall(fetchall_sql)
     if not data:
         return HttpResponse(json.dumps({"state": True, "data": result}), content_type='application/json')
Index: /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/hive/router.py
===================================================================
--- /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/hive/router.py	(revision 2350)
+++ /branches/amp_3_6_0_role/src/webui/webui/htdocs/new/src/hive/router.py	(working copy)
@@ -758,11 +758,14 @@
 def real_service(request):
     resp = {}
     if request.method == 'GET':
+        role_id = int(request.GET.get("role_id", 0))
         with open(os.path.join(an_settings.CM_ConfigFile_PATH, "rs_block.json"), 'r') as load_f:
             rsBlocks = format_block(load_f)
 
         db = DB.get_connected_db()
         select_sql = "SELECT id, name, ip_address, restapi_port, restapi_username, restapi_password, type, connection, device_group FROM device"
+        if role_id != 0:
+            select_sql = "SELECT id, name, ip_address, restapi_port, restapi_username, restapi_password, type, connection, device_group FROM device where device_group in (select device_group_name from role_device_group where role_id=%d);" % role_id
         data = db.fetchall(select_sql)
         db.close()
         key = ['id', 'name', 'ip', 'port', 'username', 'password', 'type', 'connection', 'device_group']
Index: /branches/amp_3_6_0_role/tools/tag
===================================================================
--- /branches/amp_3_6_0_role/tools/tag	(revision 2350)
+++ /branches/amp_3_6_0_role/tools/tag	(working copy)
@@ -1 +1 @@
-Beta_AMP_3_4_5_0 untagged
+Beta_AMP_3_6_0_1 untagged
