DeviceManagementServiceImpl implements DeviceManagementService { @GET @Override public Response getDevices( @QueryParam("name") String name, @QueryParam("type") String type, @QueryParam("user") String user, @QueryParam("userPattern") String userPattern, @QueryParam("role") String role, @QueryParam("ownership") String ownership, @QueryParam("status") String status, @QueryParam("groupId") int groupId, @QueryParam("since") String since, @HeaderParam("If-Modified-Since") String ifModifiedSince, @QueryParam("requireDeviceInfo") boolean requireDeviceInfo, @QueryParam("offset") int offset, @QueryParam("limit") int limit) { try { if (!StringUtils.isEmpty(name) && !StringUtils.isEmpty(role)) { return Response.status(Response.Status.BAD_REQUEST).entity( new ErrorResponse.ErrorResponseBuilder().setMessage("Request contains both name and role " + "parameters. Only one is allowed " + "at once.").build()).build(); } RequestValidationUtil.validatePaginationParameters(offset, limit); DeviceManagementProviderService dms = DeviceMgtAPIUtils.getDeviceManagementService(); DeviceAccessAuthorizationService deviceAccessAuthorizationService = DeviceMgtAPIUtils.getDeviceAccessAuthorizationService(); if (deviceAccessAuthorizationService == null) { return Response.status(Response.Status.INTERNAL_SERVER_ERROR).entity( new ErrorResponse.ErrorResponseBuilder().setMessage("Device access authorization service is " + "failed").build()).build(); } PaginationRequest request = new PaginationRequest(offset, limit); PaginationResult result; DeviceList devices = new DeviceList(); if (name != null && !name.isEmpty()) { request.setDeviceName(name); } if (type != null && !type.isEmpty()) { request.setDeviceType(type); } if (ownership != null && !ownership.isEmpty()) { RequestValidationUtil.validateOwnershipType(ownership); request.setOwnership(ownership); } if (status != null && !status.isEmpty()) { RequestValidationUtil.validateStatus(status); request.setStatus(status); } if (groupId != 0) { request.setGroupId(groupId); } if (role != null && !role.isEmpty()) { request.setOwnerRole(role); } String authorizedUser = MultitenantUtils.getTenantAwareUsername(CarbonContext.getThreadLocalCarbonContext().getUsername()); if (deviceAccessAuthorizationService.isDeviceAdminUser()) { if (user != null && !user.isEmpty()) { request.setOwner(MultitenantUtils.getTenantAwareUsername(user)); } else if (userPattern != null && !userPattern.isEmpty()) { request.setOwnerPattern(userPattern); } } else { if (user != null && !user.isEmpty()) { user = MultitenantUtils.getTenantAwareUsername(user); if (user.equals(authorizedUser)) { request.setOwner(user); } else { String msg = "User '" + authorizedUser + "' is not authorized to retrieve devices of '" + user + "' user"; log.error(msg); return Response.status(Response.Status.UNAUTHORIZED).entity( new ErrorResponse.ErrorResponseBuilder().setCode(401l).setMessage(msg).build()).build(); } } else { request.setOwner(authorizedUser); } } if (ifModifiedSince != null && !ifModifiedSince.isEmpty()) { Date sinceDate; SimpleDateFormat format = new SimpleDateFormat("EEE, d MMM yyyy HH:mm:ss Z"); try { sinceDate = format.parse(ifModifiedSince); } catch (ParseException e) { return Response.status(Response.Status.BAD_REQUEST).entity( new ErrorResponse.ErrorResponseBuilder().setMessage("Invalid date " + "string is provided in 'If-Modified-Since' header").build()).build(); } request.setSince(sinceDate); if (requireDeviceInfo) { result = dms.getAllDevices(request); } else { result = dms.getAllDevices(request, false); } if (result == null || result.getData() == null || result.getData().size() <= 0) { return Response.status(Response.Status.NOT_MODIFIED).entity("No device is modified " + "after the timestamp provided in 'If-Modified-Since' header").build(); } } else if (since != null && !since.isEmpty()) { Date sinceDate; SimpleDateFormat format = new SimpleDateFormat("EEE, d MMM yyyy HH:mm:ss Z"); try { sinceDate = format.parse(since); } catch (ParseException e) { return Response.status(Response.Status.BAD_REQUEST).entity( new ErrorResponse.ErrorResponseBuilder().setMessage("Invalid date " + "string is provided in 'since' filter").build()).build(); } request.setSince(sinceDate); if (requireDeviceInfo) { result = dms.getAllDevices(request); } else { result = dms.getAllDevices(request, false); } if (result == null || result.getData() == null || result.getData().size() <= 0) { devices.setList(new ArrayList<Device>()); devices.setCount(0); return Response.status(Response.Status.OK).entity(devices).build(); } } else { if (requireDeviceInfo) { result = dms.getAllDevices(request); } else { result = dms.getAllDevices(request, false); } int resultCount = result.getRecordsTotal(); if (resultCount == 0) { Response.status(Response.Status.OK).entity(devices).build(); } } devices.setList((List<Device>) result.getData()); devices.setCount(result.getRecordsTotal()); return Response.status(Response.Status.OK).entity(devices).build(); } catch (DeviceManagementException e) { String msg = "Error occurred while fetching all enrolled devices"; log.error(msg, e); return Response.serverError().entity( new ErrorResponse.ErrorResponseBuilder().setMessage(msg).build()).build(); } catch (DeviceAccessAuthorizationException e) { String msg = "Error occurred while checking device access authorization"; log.error(msg, e); return Response.serverError().entity( new ErrorResponse.ErrorResponseBuilder().setMessage(msg).build()).build(); } }  @GET @Path("/{type}/{id}/status") @Override Response isEnrolled(@PathParam("type") String type, @PathParam("id") String id); @GET @Override Response getDevices(
            @QueryParam("name") String name,
            @QueryParam("type") String type,
            @QueryParam("user") String user,
            @QueryParam("userPattern") String userPattern,
            @QueryParam("role") String role,
            @QueryParam("ownership") String ownership,
            @QueryParam("status") String status,
            @QueryParam("groupId") int groupId,
            @QueryParam("since") String since,
            @HeaderParam("If-Modified-Since") String ifModifiedSince,
            @QueryParam("requireDeviceInfo") boolean requireDeviceInfo,
            @QueryParam("offset") int offset,
            @QueryParam("limit") int limit); @GET @Override @Path("/user-devices") Response getDeviceByUser(@QueryParam("requireDeviceInfo") boolean requireDeviceInfo,
                                    @QueryParam("offset") int offset,
                                    @QueryParam("limit") int limit); @DELETE @Override @Path("/type/{device-type}/id/{device-id}") Response deleteDevice(@PathParam("device-type") String deviceType, @PathParam("device-id") String deviceId); @POST @Override @Path("/type/{device-type}/id/{device-id}/rename") Response renameDevice(Device device, @PathParam("device-type") String deviceType,
                                 @PathParam("device-id") String deviceId); @GET @Path("/{type}/{id}") @Override Response getDevice(
            @PathParam("type") @Size(max = 45) String type,
            @PathParam("id") @Size(max = 45) String id,
            @QueryParam("owner") @Size(max = 100) String owner,
            @HeaderParam("If-Modified-Since") String ifModifiedSince); @GET @Path("/{type}/{id}/location") @Override Response getDeviceLocation(
            @PathParam("type") @Size(max = 45) String type,
            @PathParam("id") @Size(max = 45) String id,
            @HeaderParam("If-Modified-Since") String ifModifiedSince); @GET @Path("/{type}/{id}/info") @Override Response getDeviceInformation(
            @PathParam("type") @Size(max = 45) String type,
            @PathParam("id") @Size(max = 45) String id,
            @HeaderParam("If-Modified-Since") String ifModifiedSince); @GET @Path("/{type}/{id}/features") @Override Response getFeaturesOfDevice(
            @PathParam("type") @Size(max = 45) String type,
            @PathParam("id") @Size(max = 45) String id,
            @HeaderParam("If-Modified-Since") String ifModifiedSince); @POST @Path("/search-devices") @Override Response searchDevices(@QueryParam("offset") int offset,
                                  @QueryParam("limit") int limit, SearchContext searchContext); @GET @Path("/{type}/{id}/applications") @Override Response getInstalledApplications(
            @PathParam("type") @Size(max = 45) String type,
            @PathParam("id") @Size(max = 45) String id,
            @HeaderParam("If-Modified-Since") String ifModifiedSince,
            @QueryParam("offset") int offset,
            @QueryParam("limit") int limit); @GET @Path("/{type}/{id}/operations") @Override Response getDeviceOperations(
            @PathParam("type") @Size(max = 45) String type,
            @PathParam("id") @Size(max = 45) String id,
            @HeaderParam("If-Modified-Since") String ifModifiedSince,
            @QueryParam("offset") int offset,
            @QueryParam("limit") int limit,
            @QueryParam("owner") String owner); @GET @Path("/{type}/{id}/effective-policy") @Override Response getEffectivePolicyOfDevice(@PathParam("type") @Size(max = 45) String type,
                                               @PathParam("id") @Size(max = 45) String id,
                                               @HeaderParam("If-Modified-Since") String ifModifiedSince); @GET @Path("{type}/{id}/compliance-data") Response getComplianceDataOfDevice(@PathParam("type") @Size(max = 45) String type,
                                              @PathParam("id") @Size(max = 45) String id); @PUT @Path("/{type}/{id}/changestatus") Response changeDeviceStatus(@PathParam("type") @Size(max = 45) String type,
                                       @PathParam("id") @Size(max = 45) String id,
                                       @QueryParam("newStatus") EnrolmentInfo.Status newsStatus); @POST @Path("/{type}/operations") Response addOperation(@PathParam("type") String type, @Valid OperationRequest operationRequest); static final String DATE_FORMAT_NOW; }
@Test(description = "Testing get devices when request exists both name and role.") public void testGetDevicesWhenBothNameAndRoleAvailable() { PowerMockito.stub(PowerMockito.method(DeviceMgtAPIUtils.class, "getDeviceManagementService")) .toReturn(this.deviceManagementProviderService); PowerMockito.stub(PowerMockito.method(DeviceMgtAPIUtils.class, "getDeviceAccessAuthorizationService")) .toReturn(this.deviceAccessAuthorizationService); Response response = this.deviceManagementService .getDevices(TEST_DEVICE_NAME, TEST_DEVICE_TYPE, DEFAULT_USERNAME, null, DEFAULT_ROLE, DEFAULT_OWNERSHIP, DEFAULT_STATUS, 1, null, null, false, 10, 5); Assert.assertEquals(response.getStatus(), Response.Status.BAD_REQUEST.getStatusCode()); }
@Test(description = "Testing get devices with correct request.") public void testGetDevices() { PowerMockito.stub(PowerMockito.method(DeviceMgtAPIUtils.class, "getDeviceManagementService")) .toReturn(this.deviceManagementProviderService); PowerMockito.stub(PowerMockito.method(DeviceMgtAPIUtils.class, "getDeviceAccessAuthorizationService")) .toReturn(this.deviceAccessAuthorizationService); PowerMockito.stub(PowerMockito.method(MultitenantUtils.class, "getTenantAwareUsername")) .toReturn(TENANT_AWARE_USERNAME); PowerMockito.stub(PowerMockito.method(CarbonContext.class, "getThreadLocalCarbonContext")) .toReturn(Mockito.mock(CarbonContext.class, Mockito.RETURNS_MOCKS)); Response response = this.deviceManagementService .getDevices(null, TEST_DEVICE_TYPE, DEFAULT_USERNAME, null, DEFAULT_ROLE, DEFAULT_OWNERSHIP, DEFAULT_STATUS, 1, null, null, false, 10, 5); Assert.assertEquals(response.getStatus(), Response.Status.OK.getStatusCode()); response = this.deviceManagementService .getDevices(TEST_DEVICE_NAME, TEST_DEVICE_TYPE, DEFAULT_USERNAME, null, null, DEFAULT_OWNERSHIP, DEFAULT_STATUS, 1, null, null, false, 10, 5); Assert.assertEquals(response.getStatus(), Response.Status.OK.getStatusCode()); response = this.deviceManagementService .getDevices(TEST_DEVICE_NAME, TEST_DEVICE_TYPE, null, null, null, DEFAULT_OWNERSHIP, DEFAULT_STATUS, 1, null, null, false, 10, 5); Assert.assertEquals(response.getStatus(), Response.Status.OK.getStatusCode()); response = this.deviceManagementService .getDevices(TEST_DEVICE_NAME, TEST_DEVICE_TYPE, null, null, null, DEFAULT_OWNERSHIP, DEFAULT_STATUS, 1, null, null, true, 10, 5); Assert.assertEquals(response.getStatus(), Response.Status.OK.getStatusCode()); }
@Test(description = "Testing get devices when DeviceAccessAuthorizationService is not available") public void testGetDevicesWithErroneousDeviceAccessAuthorizationService() { PowerMockito.stub(PowerMockito.method(DeviceMgtAPIUtils.class, "getDeviceManagementService")) .toReturn(this.deviceManagementProviderService); PowerMockito.stub(PowerMockito.method(DeviceMgtAPIUtils.class, "getDeviceAccessAuthorizationService")) .toReturn(null); Response response = this.deviceManagementService .getDevices(null, TEST_DEVICE_TYPE, DEFAULT_USERNAME, null, DEFAULT_ROLE, DEFAULT_OWNERSHIP, DEFAULT_STATUS, 1, null, null, false, 10, 5); Assert.assertEquals(response.getStatus(), Response.Status.INTERNAL_SERVER_ERROR.getStatusCode()); }
@Test(description = "Testing get devices when user is the device admin") public void testGetDevicesWhenUserIsAdmin() throws DeviceAccessAuthorizationException { PowerMockito.stub(PowerMockito.method(DeviceMgtAPIUtils.class, "getDeviceManagementService")) .toReturn(this.deviceManagementProviderService); PowerMockito.stub(PowerMockito.method(DeviceMgtAPIUtils.class, "getDeviceAccessAuthorizationService")) .toReturn(this.deviceAccessAuthorizationService); PowerMockito.stub(PowerMockito.method(MultitenantUtils.class, "getTenantAwareUsername")) .toReturn(TENANT_AWARE_USERNAME); PowerMockito.stub(PowerMockito.method(CarbonContext.class, "getThreadLocalCarbonContext")) .toReturn(Mockito.mock(CarbonContext.class, Mockito.RETURNS_MOCKS)); Mockito.when(deviceAccessAuthorizationService.isDeviceAdminUser()).thenReturn(true); Response response = this.deviceManagementService .getDevices(null, TEST_DEVICE_TYPE, DEFAULT_USERNAME, null, DEFAULT_ROLE, DEFAULT_OWNERSHIP, DEFAULT_STATUS, 1, null, null, false, 10, 5); Assert.assertEquals(response.getStatus(), Response.Status.OK.getStatusCode()); response = this.deviceManagementService .getDevices(null, TEST_DEVICE_TYPE, null, DEFAULT_USERNAME, DEFAULT_ROLE, DEFAULT_OWNERSHIP, DEFAULT_STATUS, 1, null, null, false, 10, 5); Assert.assertEquals(response.getStatus(), Response.Status.OK.getStatusCode()); }
@Test(description = "Testing get devices when user is unauthorized.") public void testGetDevicesWhenUserIsUnauthorized() throws Exception { PowerMockito.spy(MultitenantUtils.class); PowerMockito.stub(PowerMockito.method(DeviceMgtAPIUtils.class, "getDeviceManagementService")) .toReturn(this.deviceManagementProviderService); PowerMockito.stub(PowerMockito.method(DeviceMgtAPIUtils.class, "getDeviceAccessAuthorizationService")) .toReturn(this.deviceAccessAuthorizationService); PowerMockito.stub(PowerMockito.method(CarbonContext.class, "getThreadLocalCarbonContext")) .toReturn(Mockito.mock(CarbonContext.class, Mockito.RETURNS_MOCKS)); PowerMockito.doReturn(TENANT_AWARE_USERNAME) .when(MultitenantUtils.class, "getTenantAwareUsername", DEFAULT_USERNAME); PowerMockito.doReturn("newuser@carbon.super").when(MultitenantUtils.class, "getTenantAwareUsername", "newuser"); Mockito.when(this.deviceAccessAuthorizationService.isDeviceAdminUser()).thenReturn(false); Response response = this.deviceManagementService .getDevices(null, TEST_DEVICE_TYPE, "newuser", null, DEFAULT_ROLE, DEFAULT_OWNERSHIP, DEFAULT_STATUS, 1, null, null, false, 10, 5); Assert.assertEquals(response.getStatus(), Response.Status.UNAUTHORIZED.getStatusCode()); Mockito.reset(this.deviceAccessAuthorizationService); }
@Test(description = "Testing get devices with IF-Modified-Since") public void testGetDevicesWithModifiedSince() { String ifModifiedSince = new SimpleDateFormat(DEFAULT_DATE_FORMAT).format(new Date()); PowerMockito.stub(PowerMockito.method(DeviceMgtAPIUtils.class, "getDeviceManagementService")) .toReturn(this.deviceManagementProviderService); PowerMockito.stub(PowerMockito.method(DeviceMgtAPIUtils.class, "getDeviceAccessAuthorizationService")) .toReturn(this.deviceAccessAuthorizationService); PowerMockito.stub(PowerMockito.method(MultitenantUtils.class, "getTenantAwareUsername")) .toReturn(TENANT_AWARE_USERNAME); PowerMockito.stub(PowerMockito.method(CarbonContext.class, "getThreadLocalCarbonContext")) .toReturn(Mockito.mock(CarbonContext.class, Mockito.RETURNS_MOCKS)); Response response = this.deviceManagementService .getDevices(null, TEST_DEVICE_TYPE, DEFAULT_USERNAME, null, DEFAULT_ROLE, DEFAULT_OWNERSHIP, DEFAULT_STATUS, 1, null, ifModifiedSince, false, 10, 5); Assert.assertEquals(response.getStatus(), Response.Status.NOT_MODIFIED.getStatusCode()); response = this.deviceManagementService .getDevices(null, TEST_DEVICE_TYPE, DEFAULT_USERNAME, null, DEFAULT_ROLE, DEFAULT_OWNERSHIP, DEFAULT_STATUS, 1, null, ifModifiedSince, true, 10, 5); Assert.assertEquals(response.getStatus(), Response.Status.NOT_MODIFIED.getStatusCode()); response = this.deviceManagementService .getDevices(null, TEST_DEVICE_TYPE, DEFAULT_USERNAME, null, DEFAULT_ROLE, DEFAULT_OWNERSHIP, DEFAULT_STATUS, 1, null, "ErrorModifiedSince", false, 10, 5); Assert.assertEquals(response.getStatus(), Response.Status.BAD_REQUEST.getStatusCode()); }
@Test(description = "Testing get devices with Since") public void testGetDevicesWithSince() { String since = new SimpleDateFormat(DEFAULT_DATE_FORMAT).format(new Date()); PowerMockito.stub(PowerMockito.method(DeviceMgtAPIUtils.class, "getDeviceManagementService")) .toReturn(this.deviceManagementProviderService); PowerMockito.stub(PowerMockito.method(DeviceMgtAPIUtils.class, "getDeviceAccessAuthorizationService")) .toReturn(this.deviceAccessAuthorizationService); PowerMockito.stub(PowerMockito.method(MultitenantUtils.class, "getTenantAwareUsername")) .toReturn(TENANT_AWARE_USERNAME); PowerMockito.stub(PowerMockito.method(CarbonContext.class, "getThreadLocalCarbonContext")) .toReturn(Mockito.mock(CarbonContext.class, Mockito.RETURNS_MOCKS)); Response response = this.deviceManagementService .getDevices(null, TEST_DEVICE_TYPE, DEFAULT_USERNAME, null, DEFAULT_ROLE, DEFAULT_OWNERSHIP, DEFAULT_STATUS, 1, since, null, false, 10, 5); Assert.assertEquals(response.getStatus(), Response.Status.OK.getStatusCode()); response = this.deviceManagementService .getDevices(null, TEST_DEVICE_TYPE, DEFAULT_USERNAME, null, DEFAULT_ROLE, DEFAULT_OWNERSHIP, DEFAULT_STATUS, 1, since, null, true, 10, 5); Assert.assertEquals(response.getStatus(), Response.Status.OK.getStatusCode()); response = this.deviceManagementService .getDevices(null, TEST_DEVICE_TYPE, DEFAULT_USERNAME, null, DEFAULT_ROLE, DEFAULT_OWNERSHIP, DEFAULT_STATUS, 1, "ErrorSince", null, false, 10, 5); Assert.assertEquals(response.getStatus(), Response.Status.BAD_REQUEST.getStatusCode()); }
@Test(description = "Testing get devices when unable to retrieve devices") public void testGetDeviceServerErrorWhenGettingDeviceList() throws DeviceManagementException { PowerMockito.stub(PowerMockito.method(DeviceMgtAPIUtils.class, "getDeviceManagementService")) .toReturn(this.deviceManagementProviderService); PowerMockito.stub(PowerMockito.method(DeviceMgtAPIUtils.class, "getDeviceAccessAuthorizationService")) .toReturn(this.deviceAccessAuthorizationService); PowerMockito.stub(PowerMockito.method(MultitenantUtils.class, "getTenantAwareUsername")) .toReturn(TENANT_AWARE_USERNAME); PowerMockito.stub(PowerMockito.method(CarbonContext.class, "getThreadLocalCarbonContext")) .toReturn(Mockito.mock(CarbonContext.class, Mockito.RETURNS_MOCKS)); Mockito.when(this.deviceManagementProviderService .getAllDevices(Mockito.any(PaginationRequest.class), Mockito.anyBoolean())) .thenThrow(new DeviceManagementException()); Response response = this.deviceManagementService .getDevices(null, TEST_DEVICE_TYPE, DEFAULT_USERNAME, null, DEFAULT_ROLE, DEFAULT_OWNERSHIP, DEFAULT_STATUS, 1, null, null, false, 10, 5); Assert.assertEquals(response.getStatus(), Response.Status.INTERNAL_SERVER_ERROR.getStatusCode()); Mockito.reset(this.deviceManagementProviderService); }
@Test(description = "Testing get devices when unable to check if the user is the admin user") public void testGetDevicesServerErrorWhenCheckingAdminUser() throws DeviceAccessAuthorizationException { PowerMockito.stub(PowerMockito.method(DeviceMgtAPIUtils.class, "getDeviceManagementService")) .toReturn(this.deviceManagementProviderService); PowerMockito.stub(PowerMockito.method(DeviceMgtAPIUtils.class, "getDeviceAccessAuthorizationService")) .toReturn(this.deviceAccessAuthorizationService); PowerMockito.stub(PowerMockito.method(MultitenantUtils.class, "getTenantAwareUsername")) .toReturn(TENANT_AWARE_USERNAME); PowerMockito.stub(PowerMockito.method(CarbonContext.class, "getThreadLocalCarbonContext")) .toReturn(Mockito.mock(CarbonContext.class, Mockito.RETURNS_MOCKS)); Mockito.when(this.deviceAccessAuthorizationService.isDeviceAdminUser()) .thenThrow(new DeviceAccessAuthorizationException()); Response response = this.deviceManagementService .getDevices(null, TEST_DEVICE_TYPE, DEFAULT_USERNAME, null, DEFAULT_ROLE, DEFAULT_OWNERSHIP, DEFAULT_STATUS, 1, null, null, false, 10, 5); Assert.assertEquals(response.getStatus(), Response.Status.INTERNAL_SERVER_ERROR.getStatusCode()); Mockito.reset(this.deviceAccessAuthorizationService); }