resolve conflics

feature/appm-store/pbac
inoshperera 5 years ago
commit 83bc51b9df

@ -97,7 +97,7 @@
org.apache.synapse,
org.apache.synapse.core.axis2,
org.apache.synapse.rest,
org.wso2.carbon.certificate.mgt.core.impl
org.wso2.carbon.certificate.mgt.core.*
</Import-Package>
</instructions>
</configuration>

@ -30,6 +30,8 @@ import org.wso2.carbon.apimgt.handlers.invoker.RESTInvoker;
import org.wso2.carbon.apimgt.handlers.invoker.RESTResponse;
import org.wso2.carbon.apimgt.handlers.utils.AuthConstants;
import org.wso2.carbon.apimgt.handlers.utils.Utils;
import org.wso2.carbon.certificate.mgt.core.dto.CertificateResponse;
import org.wso2.carbon.certificate.mgt.core.exception.KeystoreException;
import org.wso2.carbon.certificate.mgt.core.impl.CertificateGenerator;
import org.wso2.carbon.context.PrivilegedCarbonContext;
@ -57,6 +59,7 @@ public class AuthenticationHandler extends AbstractHandler {
private static final String AUTHORIZATION = "Authorization";
private static final String BEARER = "Basic ";
private static final String CONTENT_TYPE = "Content-Type";
private static final boolean USE_INTERNAL_CERT_VERIFIER = true;
private IOTServerConfiguration iotServerConfiguration;
@ -125,19 +128,29 @@ public class AuthenticationHandler extends AbstractHandler {
log.debug("Verify subject DN: " + subjectDN);
}
String deviceType = this.getDeviceType(messageContext.getTo().getAddress().trim());
URI certVerifyUrl = new URI(iotServerConfiguration.getVerificationEndpoint() + deviceType);
Map<String, String> certVerifyHeaders = this.setHeaders();
Certificate certificate = new Certificate();
certificate.setPem(subjectDN);
certificate.setTenantId(tenantId);
certificate.setSerial(AuthConstants.PROXY_MUTUAL_AUTH_HEADER);
Gson gson = new Gson();
String certVerifyContent = gson.toJson(certificate);
response = restInvoker.invokePOST(certVerifyUrl, certVerifyHeaders, certVerifyContent);
if (log.isDebugEnabled()) {
log.debug("Verify response:" + response.getContent());
if (USE_INTERNAL_CERT_VERIFIER) {
CertificateResponse certificateResponse = Utils.getCertificateManagementService()
.verifySubjectDN(subjectDN);
if (certificateResponse != null && certificateResponse.getCommonName() != null
&& !certificateResponse.getCommonName().isEmpty()) {
return true;
}
} else {
String deviceType = this.getDeviceType(messageContext.getTo().getAddress().trim());
URI certVerifyUrl = new URI(iotServerConfiguration.getVerificationEndpoint() + deviceType);
Map<String, String> certVerifyHeaders = this.setHeaders();
Certificate certificate = new Certificate();
certificate.setPem(subjectDN);
certificate.setTenantId(tenantId);
certificate.setSerial(AuthConstants.PROXY_MUTUAL_AUTH_HEADER);
Gson gson = new Gson();
String certVerifyContent = gson.toJson(certificate);
response = restInvoker.invokePOST(certVerifyUrl, certVerifyHeaders, certVerifyContent);
if (log.isDebugEnabled()) {
log.debug("Verify response:" + response.getContent());
}
}
} else if (headers.containsKey(AuthConstants.MUTUAL_AUTH_HEADER)) {
javax.security.cert.X509Certificate[] certs =
@ -190,6 +203,9 @@ public class AuthenticationHandler extends AbstractHandler {
} catch (CertificateEncodingException e) {
log.error("Error while attempting to encode certificate.", e);
return false;
} catch (KeystoreException e) {
log.error("Error while attempting to validate certificate.", e);
return false;
}
}

@ -30,6 +30,8 @@ import org.wso2.carbon.apimgt.handlers.beans.DCR;
import org.wso2.carbon.apimgt.handlers.config.IOTServerConfiguration;
import org.wso2.carbon.apimgt.handlers.invoker.RESTInvoker;
import org.wso2.carbon.apimgt.handlers.invoker.RESTResponse;
import org.wso2.carbon.certificate.mgt.core.service.CertificateManagementService;
import org.wso2.carbon.context.PrivilegedCarbonContext;
import org.wso2.carbon.utils.CarbonUtils;
import javax.xml.XMLConstants;
@ -184,5 +186,20 @@ public class Utils {
}
public static CertificateManagementService getCertificateManagementService() {
PrivilegedCarbonContext ctx = PrivilegedCarbonContext.getThreadLocalCarbonContext();
CertificateManagementService certificateManagementService = (CertificateManagementService)
ctx.getOSGiService(CertificateManagementService.class, null);
if (certificateManagementService == null) {
String msg = "CertificateManagementAdminServiceImpl Management service not initialized.";
log.error(msg);
throw new IllegalStateException(msg);
}
return certificateManagementService;
}
}

@ -99,21 +99,8 @@ public class AuthenticationHandlerTest extends BaseAPIHandlerTest {
this.mockClient.reset();
}
@Test(description = "Handle request with device type URI with Proxy Mutual Auth Header",
dependsOnMethods = "testHandleSuccessfulRequestMDMCertificate")
public void testHandleSuccessRequestProxyMutualAuthHeader() throws Exception {
HashMap<String, String> transportHeaders = new HashMap<>();
transportHeaders.put(AuthConstants.PROXY_MUTUAL_AUTH_HEADER, "Test Header");
setMockClient();
this.mockClient.setResponse(getValidationResponse());
boolean response = this.handler.handleRequest(createSynapseMessageContext("<empty/>", this.synapseConfiguration,
transportHeaders, "https://test.com/testservice/device-mgt/testdevice"));
Assert.assertTrue(response);
this.mockClient.reset();
}
@Test(description = "Handle request with device type URI with Mutual Auth Header",
dependsOnMethods = "testHandleSuccessRequestProxyMutualAuthHeader")
dependsOnMethods = "testHandleSuccessfulRequestMDMCertificate")
public void testHandleSuccessRequestMutualAuthHeader() throws Exception {
HashMap<String, String> transportHeaders = new HashMap<>();
transportHeaders.put(AuthConstants.MUTUAL_AUTH_HEADER, "Test Header");

@ -99,7 +99,6 @@ public class GenericApplicationDAOImpl extends AbstractDAOImpl implements Applic
log.debug("Getting application data from the database");
log.debug(String.format("Filter: limit=%s, offset=%s", filter.getLimit(), filter.getOffset()));
}
int paramIndex = 1;
String sql = "SELECT "
+ "AP_APP.ID AS APP_ID, "
+ "AP_APP.NAME AS APP_NAME, "
@ -132,7 +131,7 @@ public class GenericApplicationDAOImpl extends AbstractDAOImpl implements Applic
+ "FROM AP_APP "
+ "INNER JOIN AP_APP_RELEASE ON "
+ "AP_APP.ID = AP_APP_RELEASE.AP_APP_ID "
+ "INNER JOIN (SELECT ID FROM AP_APP LIMIT ? OFFSET ? ) AS app_data ON app_data.ID = AP_APP.ID "
+ "INNER JOIN (SELECT ID FROM AP_APP WHERE AP_APP.TENANT_ID = ? LIMIT ? OFFSET ? ) AS app_data ON app_data.ID = AP_APP.ID "
+ "WHERE AP_APP.TENANT_ID = ?";
if (filter == null) {
@ -183,8 +182,9 @@ public class GenericApplicationDAOImpl extends AbstractDAOImpl implements Applic
try {
Connection conn = this.getDBConnection();
try (PreparedStatement stmt = conn.prepareStatement(sql);
){
try (PreparedStatement stmt = conn.prepareStatement(sql)){
int paramIndex = 1;
stmt.setInt(paramIndex++, tenantId);
if (filter.getLimit() != -1) {
if (filter.getLimit() == 0) {
stmt.setInt(paramIndex++, 100);

@ -30,6 +30,7 @@ import PolicyReport from './scenes/Home/scenes/Reports/scenes/PolicyCompliance';
import DeviceStatusReport from './scenes/Home/scenes/Reports/scenes/DeviceStatus';
import AppNotInstalledDevicesReport from './scenes/Home/scenes/Reports/scenes/AppNotInstalledDevices';
import Geo from './scenes/Home/scenes/Geo';
import EncryptionStatus from './scenes/Home/scenes/Reports/scenes/EncryptionStatus';
const routes = [
{
@ -53,11 +54,6 @@ const routes = [
// exact: true,
// },
// {
// path: '/entgra/geo',
// component: Geo,
// exact: true,
// },
// {
// path: '/entgra/devices',
// component: Devices,
// exact: true,
@ -137,6 +133,11 @@ const routes = [
component: AppNotInstalledDevicesReport,
exact: true,
},
{
path: '/entgra/reports/encryption-status',
component: EncryptionStatus,
exact: true,
},
],
},
];

@ -0,0 +1,258 @@
/*
* Copyright (c) 2020, Entgra (pvt) Ltd. (http://entgra.io) All Rights Reserved.
*
* Entgra (pvt) Ltd. licenses this file to you under the Apache License,
* Version 2.0 (the "License"); you may not use this file except
* in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
import React from 'react';
import axios from 'axios';
import { Icon, message, notification, Radio, Table, Tag, Tooltip } from 'antd';
import TimeAgo from 'javascript-time-ago';
// Load locale-specific relative date/time formatting rules.
import en from 'javascript-time-ago/locale/en';
import { withConfigContext } from '../../../../../../../../components/ConfigContext';
let config = null;
const columns = [
{
title: 'Device',
dataIndex: 'name',
},
{
title: 'Type',
dataIndex: 'type',
key: 'type',
// eslint-disable-next-line react/display-name
render: type => {
const defaultPlatformIcons = config.defaultPlatformIcons;
let icon = defaultPlatformIcons.default.icon;
let color = defaultPlatformIcons.default.color;
let theme = defaultPlatformIcons.default.theme;
if (defaultPlatformIcons.hasOwnProperty(type)) {
icon = defaultPlatformIcons[type].icon;
color = defaultPlatformIcons[type].color;
theme = defaultPlatformIcons[type].theme;
}
return (
<span style={{ fontSize: 20, color: color, textAlign: 'center' }}>
<Icon type={icon} theme={theme} />
</span>
);
},
// todo add filtering options
},
{
title: 'Owner',
dataIndex: 'enrolmentInfo',
key: 'owner',
render: enrolmentInfo => enrolmentInfo.owner,
// todo add filtering options
},
{
title: 'Ownership',
dataIndex: 'enrolmentInfo',
key: 'ownership',
render: enrolmentInfo => enrolmentInfo.ownership,
// todo add filtering options
},
{
title: 'Status',
dataIndex: 'enrolmentInfo',
key: 'status',
// eslint-disable-next-line react/display-name
render: enrolmentInfo => {
const status = enrolmentInfo.status.toLowerCase();
let color = '#f9ca24';
switch (status) {
case 'active':
color = '#badc58';
break;
case 'created':
color = '#6ab04c';
break;
case 'removed':
color = '#ff7979';
break;
case 'inactive':
color = '#f9ca24';
break;
case 'blocked':
color = '#636e72';
break;
}
return <Tag color={color}>{status}</Tag>;
},
// todo add filtering options
},
{
title: 'Last Updated',
dataIndex: 'enrolmentInfo',
key: 'dateOfLastUpdate',
// eslint-disable-next-line react/display-name
render: data => {
const { dateOfLastUpdate } = data;
const timeAgoString = getTimeAgo(dateOfLastUpdate);
return (
<Tooltip title={new Date(dateOfLastUpdate).toString()}>
{timeAgoString}
</Tooltip>
);
},
// todo add filtering options
},
];
const getTimeAgo = time => {
const timeAgo = new TimeAgo('en-US');
return timeAgo.format(time);
};
class EncryptedDeviceTable extends React.Component {
constructor(props) {
super(props);
config = this.props.context;
TimeAgo.addLocale(en);
this.state = {
data: [],
pagination: {},
loading: false,
isEncrypted: true,
};
}
componentDidMount() {
this.fetch();
}
// fetch data from api
fetch = (params = {}) => {
const config = this.props.context;
this.setState({ loading: true });
// get current page
const currentPage = params.hasOwnProperty('page') ? params.page : 1;
const extraParams = {
offset: 10 * (currentPage - 1), // calculate the offset
limit: 10,
requireDeviceInfo: true,
isEncrypted: this.state.isEncrypted,
};
const encodedExtraParams = Object.keys(extraParams)
.map(key => key + '=' + extraParams[key])
.join('&');
// send request to the invoker
axios
.get(
window.location.origin +
config.serverConfig.invoker.uri +
config.serverConfig.invoker.deviceMgt +
'/reports/encryption-status?' +
encodedExtraParams,
)
.then(res => {
if (res.status === 200) {
const pagination = { ...this.state.pagination };
this.setState({
loading: false,
data: res.data.data.devices,
pagination,
});
}
})
.catch(error => {
if (error.hasOwnProperty('response') && error.response.status === 401) {
// todo display a popop with error
message.error('You are not logged in');
window.location.href = window.location.origin + '/entgra/login';
} else {
notification.error({
message: 'There was a problem',
duration: 0,
description: 'Error occurred while trying to load devices.',
});
}
this.setState({ loading: false });
});
};
handleTableChange = (pagination, filters, sorter) => {
const pager = { ...this.state.pagination };
pager.current = pagination.current;
this.setState({
pagination: pager,
});
this.fetch({
results: pagination.pageSize,
page: pagination.current,
sortField: sorter.field,
sortOrder: sorter.order,
...filters,
});
};
handleModeChange = value => {
this.setState(
{
isEncrypted: value.target.value,
},
this.fetch,
);
};
render() {
const { data, pagination, loading } = this.state;
return (
<div>
<Radio.Group
onChange={this.handleModeChange}
defaultValue={'true'}
style={{ marginBottom: 8, marginRight: 5 }}
>
<Radio.Button value={'true'}>Enabled Devices</Radio.Button>
<Radio.Button value={'false'}>Disabled Devices</Radio.Button>
</Radio.Group>
<div style={{ backgroundColor: '#ffffff', borderRadius: 5 }}>
<Table
columns={columns}
rowKey={record =>
record.deviceIdentifier +
record.enrolmentInfo.owner +
record.enrolmentInfo.ownership
}
dataSource={data}
pagination={{
...pagination,
size: 'small',
// position: "top",
showTotal: (total, range) =>
`showing ${range[0]}-${range[1]} of ${total} devices`,
// showQuickJumper: true
}}
loading={loading}
onChange={this.handleTableChange}
/>
</div>
</div>
);
}
}
export default withConfigContext(EncryptedDeviceTable);

@ -0,0 +1,59 @@
/*
* Copyright (c) 2020, Entgra (pvt) Ltd. (http://entgra.io) All Rights Reserved.
*
* Entgra (pvt) Ltd. licenses this file to you under the Apache License,
* Version 2.0 (the "License"); you may not use this file except
* in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
import React from 'react';
import { PageHeader, Breadcrumb, Icon } from 'antd';
import { Link } from 'react-router-dom';
import EncryptedDeviceTable from './components/EncryptedDeviceTable/EncryptedDevicesTable';
class EncryptionStatus extends React.Component {
routes;
constructor(props) {
super(props);
this.routes = props.routes;
}
render() {
return (
<div>
<PageHeader style={{ paddingTop: 0 }}>
<Breadcrumb style={{ paddingBottom: 16 }}>
<Breadcrumb.Item>
<Link to="/entgra/devices">
<Icon type="home" /> Home
</Link>
</Breadcrumb.Item>
<Breadcrumb.Item>
<Link to="/entgra/reports">Reports</Link>
</Breadcrumb.Item>
<Breadcrumb.Item>Encryption Status</Breadcrumb.Item>
</Breadcrumb>
<div className="wrap">
<h3>Encryption Status Report</h3>
</div>
<EncryptedDeviceTable />
</PageHeader>
<div
style={{ background: '#f0f2f5', padding: 24, minHeight: 720 }}
></div>
</div>
);
}
}
export default EncryptionStatus;

@ -371,6 +371,56 @@ public interface ReportManagementService {
@QueryParam("limit")
int limit);
@GET
@Path("/encryption-status")
@ApiOperation(
produces = MediaType.APPLICATION_JSON,
httpMethod = "GET",
value = "Getting Details of Registered Devices filtered by encryption status",
notes = "Provides details of devices which is in provided encryption status",
tags = "Device Management",
extensions = {
@Extension(properties = {
@ExtensionProperty(name = Constants.SCOPE, value = "perm:devices:view")
})
}
)
@ApiResponses(
value = {
@ApiResponse(
code = 200,
message = "OK. \n Successfully fetched the list of devices.",
response = DeviceList.class,
responseHeaders = {
@ResponseHeader(
name = "Content-Type",
description = "The content type of the body")}),
@ApiResponse(
code = 500,
message = "Internal Server Error. " +
"\n Server error occurred while fetching the devices.",
response = ErrorResponse.class)
})
Response getDevicesByEncryptionStatus(
@ApiParam(
name = "isEncrypted",
value = "The encryption states which used to filter the devices",
required = true)
@QueryParam("isEncrypted")
boolean isEncrypted,
@ApiParam(
name = "offset",
value = "The starting pagination index for the list of filtered devices.",
defaultValue = "0")
@QueryParam("offset")
int offset,
@ApiParam(
name = "limit",
value = "Limit of the number of deices that should be returned.",
defaultValue = "5")
@QueryParam("limit")
int limit);
@GET
@Path("/devices/{device-type}/{package-name}/not-installed")
@ApiOperation(

@ -628,7 +628,6 @@ public class DeviceManagementServiceImpl implements DeviceManagementService {
deviceIdentifier.setType(type);
informationManager = DeviceMgtAPIUtils.getDeviceInformationManagerService();
deviceLocation = informationManager.getDeviceLocation(deviceIdentifier);
} catch (DeviceDetailsMgtException e) {
String msg = "Error occurred while getting the device location.";
log.error(msg, e);

@ -238,4 +238,30 @@ public class ReportManagementServiceImpl implements ReportManagementService {
return Response.status(Response.Status.INTERNAL_SERVER_ERROR).entity(msg).build();
}
}
@GET
@Path("/encryption-status")
@Override
public Response getDevicesByEncryptionStatus(@QueryParam("isEncrypted") boolean isEncrypted,
@DefaultValue("0")
@QueryParam("offset") int offset,
@DefaultValue("5")
@QueryParam("limit") int limit) {
try {
PaginationRequest request = new PaginationRequest(offset, limit);
PaginationResult paginationResult = DeviceMgtAPIUtils
.getReportManagementService()
.getDevicesByEncryptionStatus(request, isEncrypted);
DeviceList deviceList = new DeviceList();
deviceList.setList((List<Device>) paginationResult.getData());
deviceList.setCount(paginationResult.getRecordsTotal());
return Response.status(Response.Status.OK).entity(deviceList).build();
} catch (ReportManagementException e) {
String msg = "Error occurred while retrieving devices list with provided encryption status";
log.error(msg, e);
return Response.status(Response.Status.INTERNAL_SERVER_ERROR).entity(msg).build();
}
}
}

@ -759,7 +759,7 @@ public class DeviceAgentServiceTest {
List<String> deviceTypes = new ArrayList<>();
deviceTypes.add(TEST_DEVICE_TYPE);
Mockito.when(this.deviceManagementProviderService.getAvailableDeviceTypes()).thenReturn(deviceTypes);
Mockito.when(this.deviceManagementProviderService.getPendingOperations(Mockito.any())).thenThrow(new
Mockito.when(this.deviceManagementProviderService.getPendingOperations(Mockito.any(DeviceIdentifier.class))).thenThrow(new
OperationManagementException());
Response response = this.deviceAgentService.getPendingOperations(TEST_DEVICE_TYPE, TEST_DEVICE_IDENTIFIER);
Assert.assertNotNull(response, "Response should not be null");
@ -973,7 +973,7 @@ public class DeviceAgentServiceTest {
deviceTypes.add(TEST_DEVICE_TYPE);
Mockito.when(this.deviceManagementProviderService.getAvailableDeviceTypes()).thenReturn(deviceTypes);
Mockito.doThrow(new OperationManagementException()).when(this.deviceManagementProviderService)
.updateOperation(Mockito.any(), Mockito.any());
.updateOperation(Mockito.any(DeviceIdentifier.class), Mockito.any());
Response response = this.deviceAgentService.updateOperation(TEST_DEVICE_TYPE, TEST_DEVICE_IDENTIFIER,
operation);
Assert.assertNotNull(response, "The response should not be null");

@ -17,6 +17,7 @@
*/
package org.wso2.carbon.device.mgt.common.operation.mgt;
import org.wso2.carbon.device.mgt.common.Device;
import org.wso2.carbon.device.mgt.common.DeviceIdentifier;
import org.wso2.carbon.device.mgt.common.exceptions.DeviceManagementException;
import org.wso2.carbon.device.mgt.common.exceptions.InvalidDeviceException;
@ -74,8 +75,11 @@ public interface OperationManager {
* @throws OperationManagementException If some unusual behaviour is observed while fetching the
* operation list.
*/
@Deprecated
List<? extends Operation> getPendingOperations(DeviceIdentifier deviceId) throws OperationManagementException;
List<? extends Operation> getPendingOperations(Device device) throws OperationManagementException;
Operation getNextPendingOperation(DeviceIdentifier deviceId, long notNowOperationFrequency)
throws OperationManagementException;
@ -83,6 +87,8 @@ public interface OperationManager {
void updateOperation(DeviceIdentifier deviceId, Operation operation) throws OperationManagementException;
void updateOperation(int enrolmentId, Operation operation) throws OperationManagementException;
Operation getOperationByDeviceAndOperationId(DeviceIdentifier deviceId, int operationId)
throws OperationManagementException;

@ -61,6 +61,16 @@ public interface ReportManagementService {
PaginationResult getDevicesExpiredByOSVersion(PaginationRequest request)
throws ReportManagementException, DeviceTypeNotFoundException;
/**
* Get a paginated list of devices which is filtered by given encryption status
*
* @param request {@link PaginationRequest}
* @return {@link PaginationResult}
* @throws ReportManagementException Might occur during the business logic or building database query
*/
PaginationResult getDevicesByEncryptionStatus(PaginationRequest request, boolean isEncrypted)
throws ReportManagementException;
/**
* This method is used to get devices which have not installed the app with the given package name
*

@ -15,6 +15,7 @@
*/
package org.wso2.carbon.device.mgt.core.app.mgt;
import org.wso2.carbon.device.mgt.common.Device;
import org.wso2.carbon.device.mgt.common.DeviceIdentifier;
import org.wso2.carbon.device.mgt.common.app.mgt.Application;
import org.wso2.carbon.device.mgt.common.app.mgt.ApplicationManagementException;
@ -24,10 +25,17 @@ import java.util.List;
public interface ApplicationManagementProviderService extends ApplicationManager{
void updateApplicationListInstalledInDevice(DeviceIdentifier deviceIdentifier,
List<Application> applications) throws ApplicationManagementException;
@Deprecated
void updateApplicationListInstalledInDevice(DeviceIdentifier deviceIdentifier, List<Application> applications)
throws ApplicationManagementException;
void updateApplicationListInstalledInDevice(Device device, List<Application> applications)
throws ApplicationManagementException;
@Deprecated
List<Application> getApplicationListForDevice(DeviceIdentifier deviceIdentifier)
throws ApplicationManagementException;
List<Application> getApplicationListForDevice(Device device)
throws ApplicationManagementException;
}

@ -18,6 +18,7 @@
package org.wso2.carbon.device.mgt.core.app.mgt;
import com.google.gson.Gson;
import org.apache.commons.lang.StringUtils;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
@ -35,38 +36,31 @@ import org.wso2.carbon.device.mgt.common.operation.mgt.OperationManagementExcept
import org.wso2.carbon.device.mgt.core.DeviceManagementConstants;
import org.wso2.carbon.device.mgt.core.app.mgt.config.AppManagementConfig;
import org.wso2.carbon.device.mgt.core.dao.ApplicationDAO;
import org.wso2.carbon.device.mgt.core.dao.ApplicationMappingDAO;
import org.wso2.carbon.device.mgt.core.dao.DeviceDAO;
import org.wso2.carbon.device.mgt.core.dao.DeviceManagementDAOException;
import org.wso2.carbon.device.mgt.core.dao.DeviceManagementDAOFactory;
import org.wso2.carbon.device.mgt.core.internal.DeviceManagementDataHolder;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
/**
* Implements Application Manager interface
*/
public class ApplicationManagerProviderServiceImpl implements ApplicationManagementProviderService {
private DeviceDAO deviceDAO;
private ApplicationDAO applicationDAO;
private ApplicationMappingDAO applicationMappingDAO;
private static final String GET_APP_LIST_URL = "store/apis/assets/mobileapp?domain=carbon.super&page=1";
private static final Log log = LogFactory.getLog(ApplicationManagerProviderServiceImpl.class);
public ApplicationManagerProviderServiceImpl(AppManagementConfig appManagementConfig) {
this.deviceDAO = DeviceManagementDAOFactory.getDeviceDAO();
this.applicationDAO = DeviceManagementDAOFactory.getApplicationDAO();
this.applicationMappingDAO = DeviceManagementDAOFactory.getApplicationMappingDAO();
}
ApplicationManagerProviderServiceImpl() {
this.deviceDAO = DeviceManagementDAOFactory.getDeviceDAO();
this.applicationDAO = DeviceManagementDAOFactory.getApplicationDAO();
this.applicationMappingDAO = DeviceManagementDAOFactory.getApplicationMappingDAO();
}
@Override
@ -146,10 +140,8 @@ public class ApplicationManagerProviderServiceImpl implements ApplicationManagem
} catch (DeviceManagementException e) {
throw new ApplicationManagementException("Error in get devices for user: " + userName +
" in app installation", e);
} catch (OperationManagementException e) {
throw new ApplicationManagementException("Error in add operation at app installation", e);
}
}
@ -190,103 +182,114 @@ public class ApplicationManagerProviderServiceImpl implements ApplicationManagem
} catch (OperationManagementException e) {
throw new ApplicationManagementException("Error in add operation at app installation", e);
}
}
@Override
public void updateApplicationListInstalledInDevice(
DeviceIdentifier deviceIdentifier,
public void updateApplicationListInstalledInDevice(DeviceIdentifier deviceIdentifier,
List<Application> applications) throws ApplicationManagementException {
if (log.isDebugEnabled()) {
log.debug("Updating application list for device: " + deviceIdentifier.toString());
}
List<Application> installedAppList = getApplicationListForDevice(deviceIdentifier);
try {
Device device = DeviceManagementDataHolder.getInstance().getDeviceManagementProvider().getDevice(deviceIdentifier,
false);
int tenantId = CarbonContext.getThreadLocalCarbonContext().getTenantId();
Device device = DeviceManagementDataHolder.getInstance().getDeviceManagementProvider()
.getDevice(deviceIdentifier, false);
updateApplicationListInstalledInDevice(device, applications);
} catch (DeviceManagementException e) {
String msg = "Error occurred obtaining the device object for device " + deviceIdentifier.toString();
log.error(msg, e);
throw new ApplicationManagementException(msg, e);
}
}
@Override
public void updateApplicationListInstalledInDevice(Device device, List<Application> newApplications)
throws ApplicationManagementException {
if (log.isDebugEnabled()) {
log.debug("Updating application list for device: " + device.getDeviceIdentifier());
log.debug("Apps in device: " + new Gson().toJson(newApplications));
}
int tenantId = CarbonContext.getThreadLocalCarbonContext().getTenantId();
try {
DeviceManagementDAOFactory.beginTransaction();
List<Application> installedAppList = applicationDAO
.getInstalledApplications(device.getId(), device.getEnrolmentInfo().getId(), tenantId);
if (log.isDebugEnabled()) {
log.debug("Number of apps installed:" + installedAppList.size());
log.debug("Previous app list: " + new Gson().toJson(installedAppList));
}
List<Application> appsToAdd = new ArrayList<>();
List<Integer> appIdsToRemove = new ArrayList<>(installedAppList.size());
for (Application installedApp : installedAppList) {
if (!applications.contains(installedApp)) {
if (log.isDebugEnabled()) {
log.debug("Remove app Id:" + installedApp.getId());
Map<String, Application> appsToRemove = new HashMap<>();
Map<String, Application> appsToUpdate = new HashMap<>();
Map<String, Application> appsToInsert = new HashMap<>();
Map<String, Application> installedApps = new HashMap<>();
boolean removable;
for (Application installedApp: installedAppList) {
removable = true;
for (Application newApp : newApplications) {
if (newApp.getApplicationIdentifier().equals(installedApp.getApplicationIdentifier())) {
removable = false;
break;
}
appIdsToRemove.add(installedApp.getId());
}
if (removable) {
appsToRemove.put(installedApp.getApplicationIdentifier(), installedApp);
} else {
installedApps.put(installedApp.getApplicationIdentifier(), installedApp);
}
}
DeviceManagementDAOFactory.beginTransaction();
applicationMappingDAO.removeApplicationMapping(device.getId(), device.getEnrolmentInfo().getId(),
appIdsToRemove, tenantId);
Application installedApp;
List<Integer> applicationIds = new ArrayList<>();
List<Application> applicationsToMap = new ArrayList<>();
for (Application application : applications) {
// Adding N/A if application doesn't have a version. Also truncating the application version,
// if length of the version is greater than maximum allowed length.
if (application.getVersion() == null) {
application.setVersion("N/A");
} else if (application.getVersion().length() >
DeviceManagementConstants.OperationAttributes.APPLIST_VERSION_MAX_LENGTH) {
application.setVersion(StringUtils.abbreviate(application.getVersion(),
for (Application newApp : newApplications) {
if (newApp.getVersion() == null) {
newApp.setVersion("N/A");
} else if (newApp.getVersion().length()
> DeviceManagementConstants.OperationAttributes.APPLIST_VERSION_MAX_LENGTH) {
newApp.setVersion(StringUtils.abbreviate(newApp.getVersion(),
DeviceManagementConstants.OperationAttributes.APPLIST_VERSION_MAX_LENGTH));
}
if (!installedAppList.contains(application)) {
installedApp = applicationDAO.getApplication(application.getApplicationIdentifier(),
application.getVersion(), tenantId);
if (installedApp == null) {
appsToAdd.add(application);
} else {
application.setId(installedApp.getId());
applicationsToMap.add(application);
if (installedApps.containsKey(newApp.getApplicationIdentifier())) {
Application oldApp = installedApps.get(newApp.getApplicationIdentifier());
if (oldApp.isActive() != newApp.isActive() || oldApp.getMemoryUsage() != newApp.getMemoryUsage()
|| !newApp.getVersion().equals(oldApp.getVersion())) {
newApp.setId(oldApp.getId());
appsToUpdate.put(newApp.getApplicationIdentifier(), newApp);
}
} else {
appsToInsert.put(newApp.getApplicationIdentifier(), newApp);
}
}
if (log.isDebugEnabled()) {
log.debug("num of apps add:" + appsToAdd.size());
log.debug("Apps to remove: " + new Gson().toJson(appsToRemove.values()));
log.debug("Apps to update: " + new Gson().toJson(appsToUpdate.values()));
log.debug("Apps to insert: " + new Gson().toJson(appsToInsert.values()));
}
applicationIds.addAll(applicationDAO.addApplications(appsToAdd, tenantId));
// Getting the applications ids for the second time
for (Application application : appsToAdd) {
installedApp = applicationDAO.getApplication(application.getApplicationIdentifier(),
application.getVersion(), tenantId);
application.setId(installedApp.getId());
applicationsToMap.add(application);
if (!appsToRemove.isEmpty()) {
applicationDAO.removeApplications(new ArrayList<>(appsToRemove.values()), device.getId(),
device.getEnrolmentInfo().getId(), tenantId);
}
if (log.isDebugEnabled()) {
log.debug("num of app Ids:" + applicationIds.size());
if (!appsToUpdate.isEmpty()) {
applicationDAO.updateApplications(new ArrayList<>(appsToUpdate.values()), device.getId(),
device.getEnrolmentInfo().getId(), tenantId);
}
applicationMappingDAO.addApplicationMappingsWithApps(device.getId(), device.getEnrolmentInfo().getId(),
applicationsToMap, tenantId);
if (log.isDebugEnabled()) {
log.debug("num of remove app Ids:" + appIdsToRemove.size());
if (!appsToInsert.isEmpty()) {
applicationDAO.addApplications(new ArrayList<>(appsToInsert.values()), device.getId(),
device.getEnrolmentInfo().getId(), tenantId);
}
DeviceManagementDAOFactory.commitTransaction();
} catch (DeviceManagementDAOException e) {
DeviceManagementDAOFactory.rollbackTransaction();
String msg = "Error occurred saving application list of the device " + deviceIdentifier.toString();
String msg = "Error occurred saving application list of the device " + device.getDeviceIdentifier();
log.error(msg, e);
throw new ApplicationManagementException(msg, e);
} catch (TransactionManagementException e) {
String msg = "Error occurred while initializing transaction for saving application list to the device "
+ deviceIdentifier.toString();
log.error(msg, e);
throw new ApplicationManagementException(msg, e);
} catch (DeviceManagementException e) {
String msg = "Error occurred obtaining the device object for device " + deviceIdentifier.toString();
String msg =
"Error occurred while initializing transaction for saving application list to the device " + device
.getDeviceIdentifier();
log.error(msg, e);
throw new ApplicationManagementException(msg, e);
} catch (Exception e) {
String msg = "Exception occurred saving application list of the device " + deviceIdentifier.toString();
String msg = "Exception occurred saving application list of the device " + device.getDeviceIdentifier();
log.error(msg, e);
throw new ApplicationManagementException(msg, e);
} finally {
@ -312,20 +315,26 @@ public class ApplicationManagerProviderServiceImpl implements ApplicationManagem
}
return new ArrayList<>();
}
return getApplicationListForDevice(device);
}
@Override
public List<Application> getApplicationListForDevice(Device device) throws ApplicationManagementException {
int tenantId = CarbonContext.getThreadLocalCarbonContext().getTenantId();
try {
DeviceManagementDAOFactory.openConnection();
return applicationDAO.getInstalledApplications(device.getId(), device.getEnrolmentInfo().getId());
return applicationDAO.getInstalledApplications(device.getId(), device.getEnrolmentInfo().getId(), tenantId);
} catch (DeviceManagementDAOException e) {
String msg = "Error occurred while fetching the Application List of device " + deviceId.toString();
String msg = "Error occurred while fetching the Application List of device " + device.getDeviceIdentifier();
log.error(msg, e);
throw new ApplicationManagementException(msg, e);
} catch (SQLException e) {
String msg = "Error occurred while opening a connection to the data source to get application " +
"list of the device " + deviceId.toString();
"list of the device " + device.getDeviceIdentifier();
log.error(msg, e);
throw new ApplicationManagementException(msg, e);
} catch (Exception e) {
String msg = "Exception occurred getting application list of the device " + deviceId.toString();
String msg = "Exception occurred getting application list of the device " + device.getDeviceIdentifier();
log.error(msg, e);
throw new ApplicationManagementException(msg, e);
} finally {

@ -171,8 +171,6 @@ public class ArchivalServiceImpl implements ArchivalService {
openConnection();
operationResponses = archivalDAO.selectOperationResponses();
notification = archivalDAO.selectNotifications();
commandOperations = archivalDAO.selectCommandOperations();
profileOperations = archivalDAO.selectProfileOperations();
enrollmentMapping = archivalDAO.selectEnrolmentMappings();
operations = archivalDAO.selectOperations();
@ -199,18 +197,6 @@ public class ArchivalServiceImpl implements ArchivalService {
}
archivalDAO.moveNotifications(notification);
//Purge the command operations table, DM_COMMAND_OPERATION
if (log.isDebugEnabled()) {
log.debug("## Archiving command operations");
}
archivalDAO.moveCommandOperations(commandOperations);
//Purge the profile operation table, DM_PROFILE_OPERATION
if (log.isDebugEnabled()) {
log.debug("## Archiving profile operations");
}
archivalDAO.moveProfileOperations(profileOperations);
//Purge the enrolment mappings table, DM_ENROLMENT_OP_MAPPING
if (log.isDebugEnabled()) {
log.debug("## Archiving enrolment mappings");

@ -29,6 +29,10 @@ public class ArchiveOperation {
private Timestamp recievedTimeStamp;
private String operationCode;
private Object operationDetails;
private String initiatedBy;
private boolean enabled;
public int getId() {
return id;
}
@ -68,5 +72,29 @@ public class ArchiveOperation {
public void setOperationCode(String operationCode) {
this.operationCode = operationCode;
}
public Object getOperationDetails() {
return operationDetails;
}
public void setOperationDetails(Object operationDetails) {
this.operationDetails = operationDetails;
}
public String getInitiatedBy() {
return initiatedBy;
}
public void setInitiatedBy(String initiatedBy) {
this.initiatedBy = initiatedBy;
}
public boolean isEnabled() {
return enabled;
}
public void setEnabled(boolean enabled) {
this.enabled = enabled;
}
}

@ -46,12 +46,8 @@ public interface ArchivalDAO {
List<ArchiveCommandOperation> selectCommandOperations() throws ArchivalDAOException;
void moveCommandOperations(List<ArchiveCommandOperation> rs) throws ArchivalDAOException;
List<ArchiveProfileOperation> selectProfileOperations() throws ArchivalDAOException;
void moveProfileOperations(List<ArchiveProfileOperation> rs) throws ArchivalDAOException;
List<ArchiveEnrolmentOperationMap> selectEnrolmentMappings() throws ArchivalDAOException;
void moveEnrolmentMappings(List<ArchiveEnrolmentOperationMap> rs) throws ArchivalDAOException;

@ -398,56 +398,6 @@ public class ArchivalDAOImpl implements ArchivalDAO {
return commandOperations;
}
@Override
public void moveCommandOperations(List<ArchiveCommandOperation> commandOperations) throws ArchivalDAOException {
Statement stmt = null;
PreparedStatement stmt2 = null;
Statement stmt3 = null;
try {
Connection conn = ArchivalSourceDAOFactory.getConnection();
Connection conn2 = ArchivalDestinationDAOFactory.getConnection();
String sql = "INSERT INTO DM_COMMAND_OPERATION_ARCH VALUES(?,?,?)";
stmt2 = conn2.prepareStatement(sql);
int count = 0;
for (ArchiveCommandOperation rs : commandOperations) {
stmt2.setInt(1, rs.getOperationId());
stmt2.setInt(2, rs.getEnabled());
stmt2.setTimestamp(3, this.currentTimestamp);
stmt2.addBatch();
if (++count % batchSize == 0) {
stmt2.executeBatch();
if (log.isDebugEnabled()) {
log.debug("Executing Command Operations batch " + count);
}
}
}
stmt2.executeBatch();
if (log.isDebugEnabled()) {
log.debug(count + " [COMMAND_OPERATION] Records copied to the archival table. Starting deletion");
}
sql = "DELETE o.* FROM DM_COMMAND_OPERATION o\n" +
" INNER JOIN\n" +
" DM_ARCHIVED_OPERATIONS da ON o.OPERATION_ID = da.ID \n" +
"WHERE\n" +
" o.OPERATION_ID = da.ID;";
stmt3 = conn.createStatement();
int affected = stmt3.executeUpdate(sql);
if (log.isDebugEnabled()) {
log.debug(affected + " Rows deleted");
}
} catch (SQLException e) {
String msg = "Error occurred while archiving the command operation";
log.error(msg, e);
throw new ArchivalDAOException(msg, e);
} finally {
ArchivalDAOUtil.cleanupResources(stmt2);
ArchivalDAOUtil.cleanupResources(stmt3);
}
}
@Override
public List<ArchiveProfileOperation> selectProfileOperations() throws ArchivalDAOException {
Statement stmt = null;
@ -487,57 +437,6 @@ public class ArchivalDAOImpl implements ArchivalDAO {
return profileOperations;
}
@Override
public void moveProfileOperations(List<ArchiveProfileOperation> profileOperations) throws ArchivalDAOException {
Statement stmt = null;
PreparedStatement stmt2 = null;
Statement stmt3 = null;
try {
Connection conn = ArchivalSourceDAOFactory.getConnection();
Connection conn2 = ArchivalDestinationDAOFactory.getConnection();
String sql = "INSERT INTO DM_PROFILE_OPERATION_ARCH VALUES(?, ?, ?, ?)";
stmt2 = conn2.prepareStatement(sql);
int count = 0;
for (ArchiveProfileOperation rs : profileOperations) {
stmt2.setInt(1, rs.getOperationId());
stmt2.setInt(2, rs.getEnabled());
stmt2.setBytes(3, (byte[]) rs.getOperationDetails());
stmt2.setTimestamp(4, this.currentTimestamp);
stmt2.addBatch();
if (++count % batchSize == 0) {
stmt2.executeBatch();
if (log.isDebugEnabled()) {
log.debug("Executing Profile Operations batch " + count);
}
}
}
stmt2.executeBatch();
if (log.isDebugEnabled()) {
log.debug(count + " [PROFILE_OPERATION] Records copied to the archival table. Starting deletion");
}
sql = "DELETE o.* FROM DM_PROFILE_OPERATION o\n" +
" INNER JOIN\n" +
" DM_ARCHIVED_OPERATIONS da ON o.OPERATION_ID = da.ID \n" +
"WHERE\n" +
" o.OPERATION_ID = da.ID;";
stmt3 = conn.createStatement();
int affected = stmt3.executeUpdate(sql);
if (log.isDebugEnabled()) {
log.debug(affected + " Rows deleted");
}
} catch (SQLException e) {
String msg = "Error occurred while archiving the profile operation";
log.error(msg, e);
throw new ArchivalDAOException(msg, e);
} finally {
ArchivalDAOUtil.cleanupResources(stmt2);
ArchivalDAOUtil.cleanupResources(stmt3);
}
}
@Override
public List<ArchiveEnrolmentOperationMap> selectEnrolmentMappings() throws ArchivalDAOException {
@ -652,7 +551,10 @@ public class ArchivalDAOImpl implements ArchivalDAO {
" o.TYPE,\n" +
" o.CREATED_TIMESTAMP,\n" +
" o.RECEIVED_TIMESTAMP,\n" +
" o.OPERATION_CODE\n" +
" o.OPERATION_CODE,\n" +
" o.INITIATED_BY,\n" +
" o.OPERATION_DETAILS,\n" +
" o.ENABLED \n" +
"FROM\n" +
" DM_OPERATION o\n" +
" INNER JOIN\n" +
@ -668,6 +570,9 @@ public class ArchivalDAOImpl implements ArchivalDAO {
op.setCreatedTimeStamp(rs.getTimestamp("CREATED_TIMESTAMP"));
op.setRecievedTimeStamp(rs.getTimestamp("RECEIVED_TIMESTAMP"));
op.setOperationCode(rs.getString("OPERATION_CODE"));
op.setInitiatedBy(rs.getString("INITIATED_BY"));
op.setOperationDetails(rs.getObject("OPERATION_DETAILS"));
op.setEnabled(rs.getBoolean("ENABLED"));
operations.add(op);
@ -694,7 +599,7 @@ public class ArchivalDAOImpl implements ArchivalDAO {
try {
Connection conn = ArchivalSourceDAOFactory.getConnection();
Connection conn2 = ArchivalDestinationDAOFactory.getConnection();
String sql = "INSERT INTO DM_OPERATION_ARCH VALUES(?, ?, ?, ?, ?, ?)";
String sql = "INSERT INTO DM_OPERATION_ARCH VALUES(?, ?, ?, ?, ?, ?, ?, ?, ?)";
stmt2 = conn2.prepareStatement(sql);
int count = 0;
@ -704,7 +609,11 @@ public class ArchivalDAOImpl implements ArchivalDAO {
stmt2.setTimestamp(3, rs.getCreatedTimeStamp());
stmt2.setTimestamp(4, rs.getRecievedTimeStamp());
stmt2.setString(5, rs.getOperationCode());
stmt2.setTimestamp(6, this.currentTimestamp);
stmt2.setString(6, rs.getInitiatedBy());
stmt2.setBytes(7, (byte[]) rs.getOperationDetails());
stmt2.setBoolean(8, rs.isEnabled());
stmt2.setTimestamp(9, this.currentTimestamp);
stmt2.addBatch();
if (++count % batchSize == 0) {

@ -26,11 +26,14 @@ import java.util.List;
public interface ApplicationDAO {
int addApplication(Application application, int tenantId) throws DeviceManagementDAOException;
void addApplications(List<Application> applications, int deviceId, int enrolmentId, int tenantId)
throws DeviceManagementDAOException;
List<Integer> addApplications(List<Application> applications, int tenantId) throws DeviceManagementDAOException;
void updateApplications(List<Application> applications, int deviceId, int enrolmentId, int tenantId)
throws DeviceManagementDAOException;
List<Integer> removeApplications(List<Application> apps, int tenantId) throws DeviceManagementDAOException;
void removeApplications(List<Application> apps, int deviceId, int enrolmentId, int tenantId)
throws DeviceManagementDAOException;
Application getApplication(String identifier, int tenantId) throws DeviceManagementDAOException;
@ -39,7 +42,7 @@ public interface ApplicationDAO {
Application getApplication(String identifier, String version, int deviceId, int enrolmentId, int tenantId)
throws DeviceManagementDAOException;
List<Application> getInstalledApplications(int deviceId, int enrolmentId) throws DeviceManagementDAOException;
List<Application> getInstalledApplications(int deviceId, int enrolmentId, int tenantId) throws DeviceManagementDAOException;
/**
* This method is used to get a list of applications installed in all enrolled devices

@ -1,37 +0,0 @@
/*
* Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
*
* WSO2 Inc. licenses this file to you under the Apache License,
* Version 2.0 (the "License"); you may not use this file except
* in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*
*/
package org.wso2.carbon.device.mgt.core.dao;
import org.wso2.carbon.device.mgt.common.app.mgt.Application;
import java.util.List;
public interface ApplicationMappingDAO {
int addApplicationMapping(int deviceId, int applicationId, int tenantId) throws DeviceManagementDAOException;
void addApplicationMappings(int deviceId, List<Integer> applicationIds, int tenantId)
throws DeviceManagementDAOException;
void addApplicationMappingsWithApps(int deviceId, int enrolmentId, List<Application> applications, int tenantId)
throws DeviceManagementDAOException;
void removeApplicationMapping(int deviceId, int enrolmentId, List<Integer> appIdList, int tenantId)
throws DeviceManagementDAOException;
}

@ -645,6 +645,29 @@ public interface DeviceDAO {
int getCountOfDeviceExpiredByOSVersion(String deviceType, long osBuildDate, int tenantId)
throws DeviceManagementDAOException;
/**
* Get a paginated list of devices filtered by given encryption status
*
* @param request Object with device type and OS version info
* @param tenantId Id of the current tenant.
* @param isEncrypted Encryption status to be filtered.
* @return {@link List<Device>}
* @throws DeviceManagementDAOException Thrown if error occurs while database transactions
*/
List<Device> getDevicesByEncryptionStatus(PaginationRequest request, int tenantId, boolean isEncrypted)
throws DeviceManagementDAOException;
/**
* Count the number of devices devices in the given encryption status
*
* @param tenantId Id of the current tenant.
* @param isEncrypted Encryption status to be filtered.
* @return {@link Integer}
* @throws DeviceManagementDAOException Thrown if error occurs while database transactions
*/
int getCountOfDevicesByEncryptionStatus(int tenantId, boolean isEncrypted)
throws DeviceManagementDAOException;
/**
* This method is used to get devices which have not installed the app with the given package name
*
@ -674,4 +697,6 @@ public interface DeviceDAO {
int tenantId,
String packageName,
String version) throws DeviceManagementDAOException;
int getFunctioningDevicesInSystem() throws DeviceManagementDAOException;
}

@ -26,11 +26,9 @@ import org.wso2.carbon.device.mgt.common.exceptions.TransactionManagementExcepti
import org.wso2.carbon.device.mgt.common.exceptions.UnsupportedDatabaseEngineException;
import org.wso2.carbon.device.mgt.core.config.datasource.DataSourceConfig;
import org.wso2.carbon.device.mgt.core.config.datasource.JNDILookupDefinition;
import org.wso2.carbon.device.mgt.core.dao.impl.ApplicationMappingDAOImpl;
import org.wso2.carbon.device.mgt.core.dao.impl.ApplicationDAOImpl;
import org.wso2.carbon.device.mgt.core.dao.impl.DeviceTypeDAOImpl;
import org.wso2.carbon.device.mgt.core.dao.impl.EnrollmentDAOImpl;
import org.wso2.carbon.device.mgt.core.dao.impl.GenericApplicationDAOImpl;
import org.wso2.carbon.device.mgt.core.dao.impl.PostgreSQLApplicationDAOImpl;
import org.wso2.carbon.device.mgt.core.dao.impl.device.GenericDeviceDAOImpl;
import org.wso2.carbon.device.mgt.core.dao.impl.device.OracleDeviceDAOImpl;
import org.wso2.carbon.device.mgt.core.dao.impl.device.PostgreSQLDeviceDAOImpl;
@ -131,12 +129,11 @@ public class DeviceManagementDAOFactory {
if (databaseEngine != null) {
switch (databaseEngine) {
case DeviceManagementConstants.DataBaseTypes.DB_TYPE_POSTGRESQL:
return new PostgreSQLApplicationDAOImpl();
case DeviceManagementConstants.DataBaseTypes.DB_TYPE_ORACLE:
case DeviceManagementConstants.DataBaseTypes.DB_TYPE_MSSQL:
case DeviceManagementConstants.DataBaseTypes.DB_TYPE_H2:
case DeviceManagementConstants.DataBaseTypes.DB_TYPE_MYSQL:
return new GenericApplicationDAOImpl();
return new ApplicationDAOImpl();
default:
throw new UnsupportedDatabaseEngineException("Unsupported database engine : " + databaseEngine);
}
@ -144,10 +141,6 @@ public class DeviceManagementDAOFactory {
throw new IllegalStateException("Database engine has not initialized properly.");
}
public static ApplicationMappingDAO getApplicationMappingDAO() {
return new ApplicationMappingDAOImpl();
}
public static DeviceDetailsDAO getDeviceDetailsDAO() {
return new DeviceDetailsDAOImpl();
}

@ -2134,6 +2134,108 @@ public abstract class AbstractDeviceDAOImpl implements DeviceDAO {
}
}
@Override
public List<Device> getDevicesByEncryptionStatus(PaginationRequest request, int tenantId, boolean isEncrypted)
throws DeviceManagementDAOException {
try {
Connection conn = getConnection();
String sql = "" +
"SELECT e1.owner," +
"e1.ownership," +
"e1.enrolment_id," +
"e1.device_id," +
"e1.status," +
"e1.date_of_last_update," +
"e1.date_of_enrolment," +
"d.description," +
"d.NAME AS DEVICE_NAME," +
"d.device_identification," +
"t.NAME AS DEVICE_TYPE " +
"FROM dm_device d," +
"(SELECT e.owner," +
"e.ownership," +
"e.id AS ENROLMENT_ID," +
"e.device_id," +
"e.status, " +
"e.date_of_last_update, " +
"e.date_of_enrolment " +
"FROM dm_enrolment e " +
"INNER JOIN " +
"(SELECT DEVICE_ID " +
"FROM DM_DEVICE_INFO " +
"WHERE " +
"KEY_FIELD = 'encryptionEnabled' " +
"AND VALUE_FIELD = ?) AS di " +
"ON di.DEVICE_ID = e.DEVICE_ID " +
"WHERE e.tenant_id = ?) e1, " +
"dm_device_type t " +
"WHERE d.id = e1.device_id " +
"AND t.id = d.device_type_id " +
"ORDER BY e1.date_of_last_update DESC " +
"LIMIT ? OFFSET ?";
try (PreparedStatement ps = conn.prepareStatement(sql)) {
ps.setBoolean(1, isEncrypted);
ps.setInt(2, tenantId);
ps.setInt(3, request.getRowCount());
ps.setInt(4, request.getStartIndex());
try (ResultSet rs = ps.executeQuery()) {
List<Device> devices = new ArrayList<>();
if (rs.next()) {
Device device = DeviceManagementDAOUtil.loadDevice(rs);
devices.add(device);
}
return devices;
}
}
} catch (SQLException e) {
String msg = "Error occurred while building or executing queries to retrieve information " +
"of devices filtered by encryption status: " + isEncrypted;
log.error(msg, e);
throw new DeviceManagementDAOException(msg, e);
}
}
@Override
public int getCountOfDevicesByEncryptionStatus(int tenantId, boolean isEncrypted)
throws DeviceManagementDAOException {
try {
Connection conn = getConnection();
String sql = "" +
"SELECT " +
"COUNT(e1.DEVICE_ID) AS DEVICE_COUNT " +
"FROM dm_device d," +
"(SELECT e.id AS ENROLMENT_ID, " +
"e.device_id " +
"FROM dm_enrolment e " +
"INNER JOIN " +
"(SELECT DEVICE_ID " +
"FROM DM_DEVICE_INFO " +
"WHERE KEY_FIELD = 'encryptionEnabled' " +
"AND VALUE_FIELD = ?) AS di " +
"ON di.DEVICE_ID = e.DEVICE_ID " +
"WHERE e.tenant_id = ?) e1, " +
"dm_device_type t " +
"WHERE d.id = e1.device_id " +
"AND t.id = d.device_type_id ";
try (PreparedStatement ps = conn.prepareStatement(sql)) {
ps.setBoolean(1, isEncrypted);
ps.setInt(2, tenantId);
try (ResultSet rs = ps.executeQuery()) {
return rs.next() ? rs.getInt("DEVICE_COUNT") : 0;
}
}
} catch (SQLException e) {
String msg = "Error occurred while building or executing queries to retrieve the count of devices " +
"in the provided encryption status: " + isEncrypted;
log.error(msg, e);
throw new DeviceManagementDAOException(msg, e);
}
}
/***
* This method removes records of a given list of devices from the DM_DEVICE_DETAIL table
* @param conn Connection object
@ -2617,4 +2719,25 @@ public abstract class AbstractDeviceDAOImpl implements DeviceDAO {
return joiner.toString();
}
public int getFunctioningDevicesInSystem() throws DeviceManagementDAOException {
Connection conn;
PreparedStatement stmt = null;
int deviceCount = 0;
try {
conn = this.getConnection();
String sql = "SELECT COUNT(e.DEVICE_ID) AS DEVICE_COUNT FROM DM_ENROLMENT e WHERE STATUS != 'REMOVED'";
stmt = conn.prepareStatement(sql);
ResultSet rs = stmt.executeQuery();
if (rs.next()) {
deviceCount = rs.getInt("DEVICE_COUNT");
}
} catch (SQLException e) {
throw new DeviceManagementDAOException("Error occurred while fetching count of functioning devices", e);
} finally {
DeviceManagementDAOUtil.cleanupResources(stmt, null);
}
return deviceCount;
}
}

@ -41,95 +41,101 @@ import java.util.ArrayList;
import java.util.List;
import java.util.Properties;
public abstract class AbstractApplicationDAOImpl implements ApplicationDAO {
public class ApplicationDAOImpl implements ApplicationDAO {
private static final Log log = LogFactory.getLog(AbstractApplicationDAOImpl.class);
private static final Log log = LogFactory.getLog(ApplicationDAOImpl.class);
@Override
public int addApplication(Application application, int tenantId) throws DeviceManagementDAOException {
public void addApplications(List<Application> applications, int deviceId, int enrolmentId,
int tenantId) throws DeviceManagementDAOException {
Connection conn;
PreparedStatement stmt = null;
ResultSet rs = null;
ByteArrayOutputStream bao = null;
ObjectOutputStream oos = null;
int applicationId = -1;
try {
conn = this.getConnection();
stmt = conn.prepareStatement("INSERT INTO DM_APPLICATION (NAME, PLATFORM, CATEGORY, " +
"VERSION, TYPE, LOCATION_URL, IMAGE_URL, TENANT_ID, APP_PROPERTIES, APP_IDENTIFIER, MEMORY_USAGE, IS_ACTIVE) " +
"VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)");
stmt.setString(1, application.getName());
stmt.setString(2, application.getPlatform());
stmt.setString(3, application.getCategory());
stmt.setString(4, application.getVersion());
stmt.setString(5, application.getType());
stmt.setString(6, application.getLocationUrl());
stmt.setString(7, application.getImageUrl());
stmt.setInt(8, tenantId);
bao = new ByteArrayOutputStream();
oos = new ObjectOutputStream(bao);
oos.writeObject(application.getAppProperties());
stmt.setBytes(9, bao.toByteArray());
stmt.setString(10, application.getApplicationIdentifier());
stmt.setInt(11, application.getMemoryUsage());
stmt.setBoolean(12, application.isActive());
stmt.execute();
rs = stmt.getGeneratedKeys();
if (rs.next()) {
applicationId = rs.getInt(1);
stmt = conn.prepareStatement("INSERT INTO DM_APPLICATION (NAME, PLATFORM, " +
"CATEGORY, VERSION, TYPE, LOCATION_URL, IMAGE_URL, TENANT_ID, " +
"APP_IDENTIFIER, MEMORY_USAGE, IS_ACTIVE, DEVICE_ID, ENROLMENT_ID) " +
"VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)");
for (Application application : applications) {
stmt.setString(1, application.getName());
stmt.setString(2, application.getPlatform());
stmt.setString(3, application.getCategory());
stmt.setString(4, application.getVersion());
stmt.setString(5, application.getType());
stmt.setString(6, application.getLocationUrl());
stmt.setString(7, application.getImageUrl());
stmt.setInt(8, tenantId);
stmt.setString(9, application.getApplicationIdentifier());
stmt.setInt(10, application.getMemoryUsage());
stmt.setBoolean(11, application.isActive());
stmt.setInt(12, deviceId);
stmt.setInt(13, enrolmentId);
stmt.addBatch();
}
return applicationId;
stmt.executeBatch();
} catch (SQLException e) {
throw new DeviceManagementDAOException("Error occurred while adding application '" +
application.getName() + "'", e);
} catch (IOException e) {
throw new DeviceManagementDAOException("Error occurred while serializing application properties object", e);
throw new DeviceManagementDAOException("Error occurred while adding bulk application list", e);
} finally {
if (bao != null) {
try {
bao.close();
} catch (IOException e) {
log.error("Error occurred while closing ByteArrayOutputStream", e);
}
}
if (oos != null) {
try {
oos.close();
} catch (IOException e) {
log.error("Error occurred while closing ObjectOutputStream", e);
}
DeviceManagementDAOUtil.cleanupResources(stmt, null);
}
}
@Override
public void updateApplications(List<Application> applications, int deviceId, int enrolmentId,
int tenantId) throws DeviceManagementDAOException {
Connection conn;
PreparedStatement stmt = null;
try {
conn = this.getConnection();
stmt = conn.prepareStatement("UPDATE DM_APPLICATION SET NAME = ?, PLATFORM = ?, CATEGORY = ?, " +
"VERSION = ?, TYPE = ?, LOCATION_URL = ?, IMAGE_URL = ?, MEMORY_USAGE = ?, IS_ACTIVE = ? " +
"WHERE APP_IDENTIFIER = ? AND DEVICE_ID = ? AND ENROLMENT_ID = ? AND TENANT_ID = ?");
for (Application application : applications) {
stmt.setString(1, application.getName());
stmt.setString(2, application.getPlatform());
stmt.setString(3, application.getCategory());
stmt.setString(4, application.getVersion());
stmt.setString(5, application.getType());
stmt.setString(6, application.getLocationUrl());
stmt.setString(7, application.getImageUrl());
stmt.setInt(8, application.getMemoryUsage());
stmt.setBoolean(9, application.isActive());
stmt.setString(10, application.getApplicationIdentifier());
stmt.setInt(11, deviceId);
stmt.setInt(12, enrolmentId);
stmt.setInt(13, tenantId);
stmt.addBatch();
}
DeviceManagementDAOUtil.cleanupResources(stmt, rs);
stmt.executeBatch();
} catch (SQLException e) {
throw new DeviceManagementDAOException("Error occurred while adding bulk application list", e);
} finally {
DeviceManagementDAOUtil.cleanupResources(stmt, null);
}
}
@Override
public List<Integer> removeApplications(List<Application> apps, int tenantId) throws DeviceManagementDAOException {
public void removeApplications(List<Application> apps, int deviceId, int enrolmentId, int tenantId)
throws DeviceManagementDAOException {
Connection conn = null;
PreparedStatement stmt = null;
ResultSet rs = null;
List<Integer> applicationIds = new ArrayList<>();
try {
conn = this.getConnection();
conn.setAutoCommit(false);
stmt = conn.prepareStatement("DELETE DM_APPLICATION WHERE APP_IDENTIFIER = ? AND TENANT_ID = ?",
new String[]{"id"});
stmt = conn.prepareStatement("DELETE FROM DM_APPLICATION WHERE APP_IDENTIFIER = ? AND DEVICE_ID = ? " +
"AND ENROLMENT_ID = ? AND TENANT_ID = ?");
for (Application app : apps) {
stmt.setString(1, app.getApplicationIdentifier());
stmt.setInt(2, tenantId);
stmt.setInt(2, deviceId);
stmt.setInt(3, enrolmentId);
stmt.setInt(4, tenantId);
stmt.addBatch();
}
stmt.executeBatch();
rs = stmt.getGeneratedKeys();
if (rs.next()) {
applicationIds.add(rs.getInt(1));
}
return applicationIds;
} catch (SQLException e) {
try {
if (conn != null) {
@ -210,11 +216,9 @@ public abstract class AbstractApplicationDAOImpl implements ApplicationDAO {
try {
conn = this.getConnection();
stmt = conn.prepareStatement("SELECT ID, NAME, APP_IDENTIFIER, PLATFORM, CATEGORY, VERSION, TYPE, " +
"LOCATION_URL, IMAGE_URL, appmap.APP_PROPERTIES, appmap.MEMORY_USAGE, appmap.IS_ACTIVE, TENANT_ID " +
"FROM DM_APPLICATION app INNER JOIN (SELECT APPLICATION_ID, APP_PROPERTIES, MEMORY_USAGE, " +
"IS_ACTIVE FROM DM_DEVICE_APPLICATION_MAPPING WHERE DEVICE_ID = ? AND ENROLMENT_ID = ?) appmap " +
"WHERE app.APP_IDENTIFIER = ? AND app.VERSION = ? AND " +
"appmap.APPLICATION_ID = app.id AND TENANT_ID = ?");
"LOCATION_URL, IMAGE_URL, APP_PROPERTIES, MEMORY_USAGE, IS_ACTIVE, TENANT_ID " +
"FROM DM_APPLICATION WHERE DEVICE_ID = ? AND ENROLMENT_ID = ? AND APP_IDENTIFIER = ? AND " +
"VERSION = ? AND TENANT_ID = ?");
stmt.setInt(1, deviceId);
stmt.setInt(2, enrolmentId);
stmt.setString(3, identifier);
@ -239,7 +243,8 @@ public abstract class AbstractApplicationDAOImpl implements ApplicationDAO {
}
@Override
public List<Application> getInstalledApplications(int deviceId, int enrolmentId) throws DeviceManagementDAOException {
public List<Application> getInstalledApplications(int deviceId, int enrolmentId, int tenantId)
throws DeviceManagementDAOException {
Connection conn;
PreparedStatement stmt = null;
List<Application> applications = new ArrayList<>();
@ -247,16 +252,13 @@ public abstract class AbstractApplicationDAOImpl implements ApplicationDAO {
ResultSet rs = null;
try {
conn = this.getConnection();
stmt = conn.prepareStatement("Select ID, NAME, APP_IDENTIFIER, PLATFORM, CATEGORY, VERSION, TYPE, " +
"LOCATION_URL, IMAGE_URL, APPMAP.APP_PROPERTIES, APPMAP.MEMORY_USAGE, APPMAP.IS_ACTIVE, " +
"TENANT_ID From DM_APPLICATION app INNER JOIN " +
"(Select APPLICATION_ID, APP_PROPERTIES, MEMORY_USAGE, IS_ACTIVE" +
" From DM_DEVICE_APPLICATION_MAPPING WHERE DEVICE_ID=? AND ENROLMENT_ID = ?) APPMAP " +
"ON " +
"app.ID = APPMAP.APPLICATION_ID ");
stmt = conn.prepareStatement("SELECT ID, NAME, APP_IDENTIFIER, PLATFORM, CATEGORY, VERSION, TYPE, " +
"LOCATION_URL, IMAGE_URL, APP_PROPERTIES, MEMORY_USAGE, IS_ACTIVE, TENANT_ID FROM DM_APPLICATION " +
"WHERE DEVICE_ID = ? AND ENROLMENT_ID = ? AND TENANT_ID = ?");
stmt.setInt(1, deviceId);
stmt.setInt(2, enrolmentId);
stmt.setInt(3, tenantId);
rs = stmt.executeQuery();
while (rs.next()) {

@ -1,183 +0,0 @@
/*
* Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
*
* WSO2 Inc. licenses this file to you under the Apache License,
* Version 2.0 (the "License"); you may not use this file except
* in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*
*/
package org.wso2.carbon.device.mgt.core.dao.impl;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.wso2.carbon.device.mgt.common.app.mgt.Application;
import org.wso2.carbon.device.mgt.core.dao.ApplicationMappingDAO;
import org.wso2.carbon.device.mgt.core.dao.DeviceManagementDAOException;
import org.wso2.carbon.device.mgt.core.dao.DeviceManagementDAOFactory;
import org.wso2.carbon.device.mgt.core.dao.util.DeviceManagementDAOUtil;
import java.io.*;
import java.sql.*;
import java.util.List;
public class ApplicationMappingDAOImpl implements ApplicationMappingDAO {
private static final Log log = LogFactory.getLog(ApplicationMappingDAOImpl.class);
@Override
public int addApplicationMapping(int deviceId, int applicationId,
int tenantId) throws DeviceManagementDAOException {
Connection conn;
PreparedStatement stmt = null;
ResultSet rs = null;
int mappingId = -1;
try {
conn = this.getConnection();
String sql = "INSERT INTO DM_DEVICE_APPLICATION_MAPPING (DEVICE_ID, APPLICATION_ID, " +
"TENANT_ID) VALUES (?, ?, ?)";
stmt = conn.prepareStatement(sql, new String[]{"id"});
stmt.setInt(1, deviceId);
stmt.setInt(2, applicationId);
stmt.setInt(3, tenantId);
stmt.execute();
rs = stmt.getGeneratedKeys();
if (rs.next()) {
mappingId = rs.getInt(1);
}
return mappingId;
} catch (SQLException e) {
throw new DeviceManagementDAOException("Error occurred while adding device application mapping", e);
} finally {
DeviceManagementDAOUtil.cleanupResources(stmt, rs);
}
}
@Override
public void addApplicationMappings(int deviceId, List<Integer> applicationIds,
int tenantId) throws DeviceManagementDAOException {
Connection conn;
PreparedStatement stmt = null;
ResultSet rs = null;
try {
conn = this.getConnection();
String sql = "INSERT INTO DM_DEVICE_APPLICATION_MAPPING (DEVICE_ID, APPLICATION_ID, " +
"TENANT_ID) VALUES (?, ?, ?)";
conn.setAutoCommit(false);
stmt = conn.prepareStatement(sql);
for (int applicationId : applicationIds) {
stmt.setInt(1, deviceId);
stmt.setInt(2, applicationId);
stmt.setInt(3, tenantId);
stmt.addBatch();
}
stmt.executeBatch();
} catch (SQLException e) {
throw new DeviceManagementDAOException("Error occurred while adding device application mappings", e);
} finally {
DeviceManagementDAOUtil.cleanupResources(stmt, rs);
}
}
@Override
public void addApplicationMappingsWithApps(int deviceId, int enrolmentId, List<Application> applications, int tenantId)
throws DeviceManagementDAOException {
Connection conn;
PreparedStatement stmt = null;
ResultSet rs = null;
ByteArrayOutputStream bao = null;
ObjectOutputStream oos = null;
try {
conn = this.getConnection();
String sql = "INSERT INTO DM_DEVICE_APPLICATION_MAPPING (DEVICE_ID, ENROLMENT_ID, APPLICATION_ID, " +
"APP_PROPERTIES, MEMORY_USAGE, IS_ACTIVE, TENANT_ID) VALUES (?, ?, ?, ?, ?, ?, ?)";
conn.setAutoCommit(false);
stmt = conn.prepareStatement(sql);
for (Application application : applications) {
stmt.setInt(1, deviceId);
stmt.setInt(2, enrolmentId);
stmt.setInt(3, application.getId());
bao = new ByteArrayOutputStream();
oos = new ObjectOutputStream(bao);
oos.writeObject(application.getAppProperties());
stmt.setBytes(4, bao.toByteArray());
stmt.setInt(5, application.getMemoryUsage());
stmt.setBoolean(6, application.isActive());
stmt.setInt(7, tenantId);
stmt.addBatch();
}
stmt.executeBatch();
} catch (SQLException e) {
throw new DeviceManagementDAOException("Error occurred while adding device application mappings", e);
} catch (IOException e) {
throw new DeviceManagementDAOException("Error occurred while serializing application properties object", e);
} finally {
if (bao != null) {
try {
bao.close();
} catch (IOException e) {
log.error("Error occurred while closing ByteArrayOutputStream", e);
}
}
if (oos != null) {
try {
oos.close();
} catch (IOException e) {
log.error("Error occurred while closing ObjectOutputStream", e);
}
}
DeviceManagementDAOUtil.cleanupResources(stmt, rs);
}
}
@Override
public void removeApplicationMapping(int deviceId, int enrolmentId, List<Integer> appIdList,
int tenantId) throws DeviceManagementDAOException {
Connection conn;
PreparedStatement stmt = null;
try {
String sql = "DELETE FROM DM_DEVICE_APPLICATION_MAPPING WHERE DEVICE_ID = ? AND " +
"APPLICATION_ID = ? AND TENANT_ID = ? AND ENROLMENT_ID = ?";
conn = this.getConnection();
for (int appId : appIdList) {
stmt = conn.prepareStatement(sql);
stmt.setInt(1, deviceId);
stmt.setInt(2, appId);
stmt.setInt(3, tenantId);
stmt.setInt(4, enrolmentId);
stmt.execute();
}
} catch (SQLException e) {
throw new DeviceManagementDAOException("Error occurred while removing device application mapping", e);
} finally {
DeviceManagementDAOUtil.cleanupResources(stmt, null);
}
}
private Connection getConnection() throws SQLException {
return DeviceManagementDAOFactory.getConnection();
}
}

@ -1,91 +0,0 @@
/*
* Copyright (c) 2018 WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
*
* WSO2 Inc. licenses this file to you under the Apache License,
* Version 2.0 (the "License"); you may not use this file except
* in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
package org.wso2.carbon.device.mgt.core.dao.impl;
import org.wso2.carbon.device.mgt.common.app.mgt.Application;
import org.wso2.carbon.device.mgt.core.dao.DeviceManagementDAOException;
import org.wso2.carbon.device.mgt.core.dao.DeviceManagementDAOFactory;
import org.wso2.carbon.device.mgt.core.dao.util.DeviceManagementDAOUtil;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;
/**
* Generic DAO implementation for Application Management Operations
*/
public class GenericApplicationDAOImpl extends AbstractApplicationDAOImpl{
@Override
public List<Integer> addApplications(List<Application> applications,
int tenantId) throws DeviceManagementDAOException {
Connection conn;
PreparedStatement stmt = null;
ResultSet rs;
List<Integer> applicationIds = new ArrayList<>();
try {
conn = this.getConnection();
stmt = conn.prepareStatement("INSERT INTO DM_APPLICATION (NAME, PLATFORM, " +
"CATEGORY, VERSION, TYPE, LOCATION_URL, IMAGE_URL, TENANT_ID,APP_PROPERTIES, " +
"APP_IDENTIFIER, MEMORY_USAGE, IS_ACTIVE) " +
"VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)", new String[]{"id"});
for (Application application : applications) {
stmt.setString(1, application.getName());
stmt.setString(2, application.getPlatform());
stmt.setString(3, application.getCategory());
stmt.setString(4, application.getVersion());
stmt.setString(5, application.getType());
stmt.setString(6, application.getLocationUrl());
stmt.setString(7, application.getImageUrl());
stmt.setInt(8, tenantId);
// Removing the application properties saving from the application table.
stmt.setBigDecimal(9, null);
stmt.setString(10, application.getApplicationIdentifier());
// Removing the application memory
stmt.setInt(11, 0);
stmt.setBoolean(12, true);
stmt.executeUpdate();
rs = stmt.getGeneratedKeys();
if (rs.next()) {
applicationIds.add(rs.getInt(1));
}
}
return applicationIds;
} catch (SQLException e) {
throw new DeviceManagementDAOException("Error occurred while adding bulk application list", e);
} finally {
DeviceManagementDAOUtil.cleanupResources(stmt, null);
}
}
private Connection getConnection() throws SQLException {
return DeviceManagementDAOFactory.getConnection();
}
}

@ -1,90 +0,0 @@
/*
* Copyright (c) 2018 WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
*
* WSO2 Inc. licenses this file to you under the Apache License,
* Version 2.0 (the "License"); you may not use this file except
* in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
package org.wso2.carbon.device.mgt.core.dao.impl;
import org.wso2.carbon.device.mgt.common.app.mgt.Application;
import org.wso2.carbon.device.mgt.core.dao.DeviceManagementDAOException;
import org.wso2.carbon.device.mgt.core.dao.DeviceManagementDAOFactory;
import org.wso2.carbon.device.mgt.core.dao.util.DeviceManagementDAOUtil;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;
/**
* PosgreSQL specific DAO implementation for Application Management Operations
*/
public class PostgreSQLApplicationDAOImpl extends AbstractApplicationDAOImpl{
@Override
public List<Integer> addApplications(List<Application> applications,
int tenantId) throws DeviceManagementDAOException {
Connection conn;
PreparedStatement stmt = null;
ResultSet rs;
List<Integer> applicationIds = new ArrayList<>();
try {
conn = this.getConnection();
stmt = conn.prepareStatement("INSERT INTO DM_APPLICATION (NAME, PLATFORM, " +
"CATEGORY, VERSION, TYPE, LOCATION_URL, IMAGE_URL, TENANT_ID,APP_PROPERTIES, " +
"APP_IDENTIFIER, MEMORY_USAGE, IS_ACTIVE) " +
"VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)", new String[]{"id"});
for (Application application : applications) {
stmt.setString(1, application.getName());
stmt.setString(2, application.getPlatform());
stmt.setString(3, application.getCategory());
stmt.setString(4, application.getVersion());
stmt.setString(5, application.getType());
stmt.setString(6, application.getLocationUrl());
stmt.setString(7, application.getImageUrl());
stmt.setInt(8, tenantId);
// Removing the application properties saving from the application table.
stmt.setBytes(9, null);
stmt.setString(10, application.getApplicationIdentifier());
// Removing the application memory
stmt.setInt(11, 0);
stmt.setBoolean(12, true);
stmt.executeUpdate();
rs = stmt.getGeneratedKeys();
if (rs.next()) {
applicationIds.add(rs.getInt(1));
}
}
return applicationIds;
} catch (SQLException e) {
throw new DeviceManagementDAOException("Error occurred while adding bulk application list", e);
} finally {
DeviceManagementDAOUtil.cleanupResources(stmt, null);
}
}
private Connection getConnection() throws SQLException {
return DeviceManagementDAOFactory.getConnection();
}
}

@ -894,6 +894,70 @@ public class OracleDeviceDAOImpl extends AbstractDeviceDAOImpl {
}
}
@Override
public List<Device> getDevicesByEncryptionStatus(PaginationRequest request, int tenantId, boolean isEncrypted)
throws DeviceManagementDAOException {
try {
Connection conn = getConnection();
String sql = "" +
"SELECT e1.owner, " +
"e1.ownership, " +
"e1.enrolment_id, " +
"e1.device_id, " +
"e1.status, " +
"e1.date_of_last_update, " +
"e1.date_of_enrolment, " +
"d.description, " +
"d.NAME AS DEVICE_NAME, " +
"d.device_identification, " +
"t.NAME AS DEVICE_TYPE " +
"FROM dm_device d, " +
"(SELECT e.owner, " +
"e.ownership, " +
"e.id AS ENROLMENT_ID, " +
"e.device_id, " +
"e.status, " +
"e.date_of_last_update, " +
"e.date_of_enrolment " +
"FROM dm_enrolment e " +
"INNER JOIN " +
"(SELECT DEVICE_ID " +
"FROM DM_DEVICE_INFO " +
"WHERE " +
"KEY_FIELD = 'encryptionEnabled' " +
"AND VALUE_FIELD = ?) AS di " +
"ON di.DEVICE_ID = e.DEVICE_ID " +
"WHERE e.tenant_id = ?) e1, " +
"dm_device_type t " +
"WHERE d.id = e1.device_id " +
"AND t.id = d.device_type_id " +
"ORDER BY e1.date_of_last_update DESC " +
"OFFSET ? ROWS " +
"FETCH NEXT ? ROWS ONLY";
try (PreparedStatement ps = conn.prepareStatement(sql)) {
ps.setBoolean(1, isEncrypted);
ps.setInt(2, tenantId);
ps.setInt(3, request.getStartIndex());
ps.setInt(4, request.getRowCount());
try (ResultSet rs = ps.executeQuery()) {
List<Device> devices = new ArrayList<>();
if (rs.next()) {
Device device = DeviceManagementDAOUtil.loadDevice(rs);
devices.add(device);
}
return devices;
}
}
} catch (SQLException e) {
String msg = "Error occurred while building or executing queries to retrieve information " +
"of devices filtered by encryption status: " + isEncrypted;
log.error(msg, e);
throw new DeviceManagementDAOException(msg, e);
}
}
private Connection getConnection() throws SQLException {
return DeviceManagementDAOFactory.getConnection();
}

@ -42,9 +42,16 @@ public interface DeviceInformationManager {
* @param deviceInfo - Device info object.
* @throws DeviceDetailsMgtException
*/
//void addDeviceInfo(DeviceInfo deviceInfo) throws DeviceDetailsMgtException;
@Deprecated
void addDeviceInfo(DeviceIdentifier deviceId, DeviceInfo deviceInfo) throws DeviceDetailsMgtException;
/**
* This method will manage the storing of the device information as key value pairs.
* @param deviceInfo - Device info object.
* @throws DeviceDetailsMgtException
*/
void addDeviceInfo(Device device, DeviceInfo deviceInfo) throws DeviceDetailsMgtException;
/**
* This method will return the device information.
* @param deviceIdentifier - Device identifier, device type.
@ -68,6 +75,8 @@ public interface DeviceInformationManager {
*/
void addDeviceLocation(DeviceLocation deviceLocation) throws DeviceDetailsMgtException;
void addDeviceLocation(Device device, DeviceLocation deviceLocation) throws DeviceDetailsMgtException;
/**
* This method will return the device location with latitude, longitude, address etc..
* @param deviceIdentifier - Device identifier, device type.

@ -50,6 +50,9 @@ public interface DeviceDetailsDAO {
void addDeviceProperties(Map<String, String> propertyMap, int deviceId, int enrolmentId)
throws DeviceDetailsMgtDAOException;
void updateDeviceProperties(Map<String, String> propertyMap, int deviceId, int enrolmentId)
throws DeviceDetailsMgtDAOException;
/**
* This method will return the device information when device id is provided.
* @param deviceId - device Id
@ -112,6 +115,10 @@ public interface DeviceDetailsDAO {
void addDeviceLocationInfo(Device device, DeviceLocation deviceLocation, int tenantId)
throws DeviceDetailsMgtDAOException;
void updateDeviceInformation(int deviceId, int enrollmentId, DeviceInfo newDeviceInfo) throws DeviceDetailsMgtDAOException;
void updateDeviceLocation(DeviceLocation deviceLocation, int enrollmentId) throws DeviceDetailsMgtDAOException;
// /**
// * This method will add device application to database.
// * @param deviceApplication - Device application

@ -119,6 +119,38 @@ public class DeviceDetailsDAOImpl implements DeviceDetailsDAO {
}
@Override
public void updateDeviceProperties(Map<String, String> propertyMap, int deviceId, int enrolmentId)
throws DeviceDetailsMgtDAOException {
if (propertyMap.isEmpty()) {
if(log.isDebugEnabled()) {
log.debug("Property map of device id :" + deviceId + " is empty.");
}
return;
}
Connection conn;
PreparedStatement stmt = null;
try {
conn = this.getConnection();
stmt = conn.prepareStatement("UPDATE DM_DEVICE_INFO SET VALUE_FIELD = ? WHERE DEVICE_ID = ?" +
" AND KEY_FIELD = ? AND ENROLMENT_ID = ?");
for (Map.Entry<String, String> entry : propertyMap.entrySet()) {
stmt.setString(1, entry.getValue());
stmt.setInt(2, deviceId);
stmt.setString(3, entry.getKey());
stmt.setInt(4, enrolmentId);
stmt.addBatch();
}
stmt.executeBatch();
} catch (SQLException e) {
throw new DeviceDetailsMgtDAOException("Error occurred while updating device properties to database.", e);
} finally {
DeviceManagementDAOUtil.cleanupResources(stmt, null);
}
}
@Override
public DeviceInfo getDeviceInformation(int deviceId, int enrolmentId) throws DeviceDetailsMgtDAOException {
Connection conn;
@ -135,9 +167,9 @@ public class DeviceDetailsDAOImpl implements DeviceDetailsDAO {
rs = stmt.executeQuery();
if (rs.next()) {
deviceInfo = new DeviceInfo();
// deviceInfo.setIMEI(rs.getString("IMEI"));
// deviceInfo.setIMSI(rs.getString("IMSI"));
deviceInfo = new DeviceInfo();
deviceInfo.setDeviceModel(rs.getString("DEVICE_MODEL"));
deviceInfo.setVendor(rs.getString("VENDOR"));
deviceInfo.setOsVersion(rs.getString("OS_VERSION"));
@ -267,13 +299,43 @@ public class DeviceDetailsDAOImpl implements DeviceDetailsDAO {
}
}
@Override
public void updateDeviceLocation(DeviceLocation deviceLocation, int enrollmentId)
throws DeviceDetailsMgtDAOException {
Connection conn;
PreparedStatement stmt = null;
try {
conn = this.getConnection();
stmt = conn.prepareStatement("UPDATE DM_DEVICE_LOCATION SET LATITUDE = ?, LONGITUDE = ?, " +
"STREET1 = ?, STREET2 = ?, CITY = ?, ZIP = ?, STATE = ?, COUNTRY = ?, GEO_HASH = ?, " +
"UPDATE_TIMESTAMP = ? WHERE DEVICE_ID = ? AND ENROLMENT_ID = ?");
stmt.setDouble(1, deviceLocation.getLatitude());
stmt.setDouble(2, deviceLocation.getLongitude());
stmt.setString(3, deviceLocation.getStreet1());
stmt.setString(4, deviceLocation.getStreet2());
stmt.setString(5, deviceLocation.getCity());
stmt.setString(6, deviceLocation.getZip());
stmt.setString(7, deviceLocation.getState());
stmt.setString(8, deviceLocation.getCountry());
stmt.setString(9, GeoHashGenerator.encodeGeohash(deviceLocation));
stmt.setLong(10, System.currentTimeMillis());
stmt.setInt(11, deviceLocation.getDeviceId());
stmt.setInt(12, enrollmentId);
stmt.execute();
} catch (SQLException e) {
throw new DeviceDetailsMgtDAOException("Error occurred while adding the device location to database.", e);
} finally {
DeviceManagementDAOUtil.cleanupResources(stmt, null);
}
}
@Override
public DeviceLocation getDeviceLocation(int deviceId, int enrollmentId) throws DeviceDetailsMgtDAOException {
Connection conn;
PreparedStatement stmt = null;
ResultSet rs = null;
DeviceLocation location = new DeviceLocation();
DeviceLocation location = null;
try {
conn = this.getConnection();
String sql = "SELECT * FROM DM_DEVICE_LOCATION WHERE DEVICE_ID = ? AND ENROLMENT_ID = ?";
@ -282,7 +344,8 @@ public class DeviceDetailsDAOImpl implements DeviceDetailsDAO {
stmt.setInt(2, enrollmentId);
rs = stmt.executeQuery();
while (rs.next()) {
if (rs.next()) {
location = new DeviceLocation();
location.setDeviceId(deviceId);
location.setLatitude(rs.getDouble("LATITUDE"));
location.setLongitude(rs.getDouble("LONGITUDE"));
@ -294,7 +357,6 @@ public class DeviceDetailsDAOImpl implements DeviceDetailsDAO {
location.setCountry(rs.getString("COUNTRY"));
location.setUpdatedTime(new java.util.Date(rs.getLong("UPDATE_TIMESTAMP")));
}
location.setDeviceId(deviceId);
return location;
} catch (SQLException e) {
@ -363,6 +425,47 @@ public class DeviceDetailsDAOImpl implements DeviceDetailsDAO {
}
}
@Override
public void updateDeviceInformation(int deviceId, int enrollmentId, DeviceInfo newDeviceInfo) throws DeviceDetailsMgtDAOException {
Connection conn;
PreparedStatement stmt = null;
try {
conn = this.getConnection();
stmt = conn.prepareStatement("UPDATE DM_DEVICE_DETAIL SET DEVICE_MODEL = ?, VENDOR = ?, " +
"OS_VERSION = ?, OS_BUILD_DATE = ?, BATTERY_LEVEL = ?, INTERNAL_TOTAL_MEMORY = ?, " +
"INTERNAL_AVAILABLE_MEMORY = ?, EXTERNAL_TOTAL_MEMORY = ?, EXTERNAL_AVAILABLE_MEMORY = ?, " +
"CONNECTION_TYPE = ?, SSID = ?, CPU_USAGE = ?, TOTAL_RAM_MEMORY = ?, AVAILABLE_RAM_MEMORY = ?, " +
"PLUGGED_IN = ?, UPDATE_TIMESTAMP = ? WHERE DEVICE_ID = ? AND ENROLMENT_ID = ?");
stmt.setString(1, newDeviceInfo.getDeviceModel());
stmt.setString(2, newDeviceInfo.getVendor());
stmt.setString(3, newDeviceInfo.getOsVersion());
stmt.setString(4, newDeviceInfo.getOsBuildDate());
stmt.setDouble(5, newDeviceInfo.getBatteryLevel());
stmt.setDouble(6, newDeviceInfo.getInternalTotalMemory());
stmt.setDouble(7, newDeviceInfo.getInternalAvailableMemory());
stmt.setDouble(8, newDeviceInfo.getExternalTotalMemory());
stmt.setDouble(9, newDeviceInfo.getExternalAvailableMemory());
stmt.setString(10, newDeviceInfo.getConnectionType());
stmt.setString(11, newDeviceInfo.getSsid());
stmt.setDouble(12, newDeviceInfo.getCpuUsage());
stmt.setDouble(13, newDeviceInfo.getTotalRAMMemory());
stmt.setDouble(14, newDeviceInfo.getAvailableRAMMemory());
stmt.setBoolean(15, newDeviceInfo.isPluggedIn());
stmt.setLong(16, System.currentTimeMillis());
stmt.setInt(17, deviceId);
stmt.setInt(18, enrollmentId);
stmt.execute();
} catch (SQLException e) {
throw new DeviceDetailsMgtDAOException("Error occurred while updating device details.", e);
} finally {
DeviceManagementDAOUtil.cleanupResources(stmt, null);
}
}
private Connection getConnection() throws SQLException {
return DeviceManagementDAOFactory.getConnection();
}

@ -16,7 +16,6 @@
* under the License.
*/
package org.wso2.carbon.device.mgt.core.device.details.mgt.impl;
import org.apache.commons.logging.Log;
@ -78,34 +77,65 @@ public class DeviceInformationManagerImpl implements DeviceInformationManager {
try {
Device device = DeviceManagementDataHolder.getInstance().
getDeviceManagementProvider().getDevice(deviceId, false);
addDeviceInfo(device, deviceInfo);
} catch (DeviceManagementException e) {
DeviceManagementDAOFactory.rollbackTransaction();
throw new DeviceDetailsMgtException("Error occurred while retrieving the device information.", e);
}
}
@Override
public void addDeviceInfo(Device device, DeviceInfo deviceInfo) throws DeviceDetailsMgtException {
try {
publishEvents(device, deviceInfo);
DeviceManagementDAOFactory.beginTransaction();
DeviceInfo newDeviceInfo;
DeviceInfo previousDeviceInfo = deviceDetailsDAO.getDeviceInformation(device.getId(),
device.getEnrolmentInfo().getId());
Map<String, String> previousDeviceProperties = deviceDetailsDAO.getDeviceProperties(device.getId(),
device.getEnrolmentInfo().getId());
if (previousDeviceInfo != null && previousDeviceProperties != null) {
previousDeviceInfo.setDeviceDetailsMap(previousDeviceProperties);
newDeviceInfo = processDeviceInfo(previousDeviceInfo, deviceInfo);
} else if (previousDeviceInfo == null && previousDeviceProperties != null) {
previousDeviceInfo = new DeviceInfo();
previousDeviceInfo.setDeviceDetailsMap(previousDeviceProperties);
if (previousDeviceInfo != null) {
previousDeviceInfo.setDeviceDetailsMap(new HashMap<>());
newDeviceInfo = processDeviceInfo(previousDeviceInfo, deviceInfo);
deviceDetailsDAO.updateDeviceInformation(device.getId(), device.getEnrolmentInfo().getId(),
newDeviceInfo);
} else {
deviceDetailsDAO.addDeviceInformation(device.getId(), device.getEnrolmentInfo().getId(), deviceInfo);
newDeviceInfo = deviceInfo;
}
if (previousDeviceProperties.isEmpty()) {
deviceDetailsDAO.addDeviceProperties(newDeviceInfo.getDeviceDetailsMap(), device.getId(),
device.getEnrolmentInfo().getId());
} else {
Map<String, String> updatableProps = new HashMap<>();
Map<String, String> injectableProps = new HashMap<>();
for (String key : newDeviceInfo.getDeviceDetailsMap().keySet()) {
if (previousDeviceProperties.containsKey(key)) {
updatableProps.put(key, newDeviceInfo.getDeviceDetailsMap().get(key));
} else {
injectableProps.put(key, newDeviceInfo.getDeviceDetailsMap().get(key));
}
}
deviceDetailsDAO.updateDeviceProperties(updatableProps, device.getId(),
device.getEnrolmentInfo().getId());
deviceDetailsDAO.addDeviceProperties(injectableProps, device.getId(),
device.getEnrolmentInfo().getId());
}
deviceDAO.updateDevice(device, CarbonContext.getThreadLocalCarbonContext().getTenantId());
deviceDetailsDAO.deleteDeviceInformation(device.getId(), device.getEnrolmentInfo().getId());
deviceDetailsDAO.deleteDeviceProperties(device.getId(), device.getEnrolmentInfo().getId());
deviceDetailsDAO.addDeviceInformation(device.getId(), device.getEnrolmentInfo().getId(), newDeviceInfo);
deviceDetailsDAO.addDeviceProperties(newDeviceInfo.getDeviceDetailsMap(), device.getId(),
device.getEnrolmentInfo().getId());
DeviceManagementDAOFactory.commitTransaction();
String reportingHost = System.getProperty(DeviceManagementConstants.Report
.REPORTING_EVENT_HOST);
if (reportingHost != null && !reportingHost.isEmpty()) {
DeviceDetailsWrapper deviceDetailsWrapper = new DeviceDetailsWrapper();
deviceDetailsWrapper.setDevice(device);
deviceDetailsWrapper.setDeviceInfo(deviceInfo);
deviceDetailsWrapper.getJSONString();
HttpReportingUtil.invokeApi(deviceDetailsWrapper.getJSONString(),
reportingHost + DeviceManagementConstants.Report.DEVICE_INFO_ENDPOINT);
}
//TODO :: This has to be fixed by adding the enrollment ID.
if (DeviceManagerUtil.isPublishDeviceInfoResponseEnabled()) {
Object[] metaData = {device.getDeviceIdentifier(), device.getType()};
@ -147,11 +177,14 @@ public class DeviceInformationManagerImpl implements DeviceInformationManager {
} catch (DeviceManagementDAOException e) {
DeviceManagementDAOFactory.rollbackTransaction();
throw new DeviceDetailsMgtException("Error occurred while updating the last update timestamp of the " +
"device", e);
"device", e);
} catch (DataPublisherConfigurationException e) {
DeviceManagementDAOFactory.rollbackTransaction();
throw new DeviceDetailsMgtException("Error occurred while publishing the device location information.", e);
}finally {
} catch (EventPublishingException e) {
DeviceManagementDAOFactory.rollbackTransaction();
throw new DeviceDetailsMgtException("Error occurred while sending events", e);
} finally {
DeviceManagementDAOFactory.closeConnection();
}
}
@ -263,17 +296,28 @@ public class DeviceInformationManagerImpl implements DeviceInformationManager {
@Override
public void addDeviceLocation(DeviceLocation deviceLocation) throws DeviceDetailsMgtException {
try {
Device device = DeviceManagementDataHolder.getInstance().
getDeviceManagementProvider().getDevice(deviceLocation.getDeviceIdentifier(), false);
addDeviceLocation(device, deviceLocation);
} catch (DeviceManagementException e) {
throw new DeviceDetailsMgtException("Error occurred while updating the last updated timestamp of " +
"the device", e);
}
}
@Override
public void addDeviceLocation(Device device, DeviceLocation deviceLocation) throws DeviceDetailsMgtException {
try {
deviceLocation.setDeviceId(device.getId());
DeviceManagementDAOFactory.beginTransaction();
deviceDAO.updateDevice(device, CarbonContext.getThreadLocalCarbonContext().getTenantId());
deviceDetailsDAO.addDeviceLocationInfo(device, deviceLocation,
CarbonContext.getThreadLocalCarbonContext().getTenantId());
deviceDetailsDAO.deleteDeviceLocation(deviceLocation.getDeviceId(), device.getEnrolmentInfo().getId());
deviceDetailsDAO.addDeviceLocation(deviceLocation, device.getEnrolmentInfo().getId());
DeviceLocation previousLocation = deviceDetailsDAO.getDeviceLocation(device.getId(),
device.getEnrolmentInfo().getId());
if (previousLocation == null) {
deviceDetailsDAO.addDeviceLocation(deviceLocation, device.getEnrolmentInfo().getId());
} else {
deviceDetailsDAO.updateDeviceLocation(deviceLocation, device.getEnrolmentInfo().getId());
}
if (DeviceManagerUtil.isPublishLocationResponseEnabled()) {
Object[] metaData = {device.getDeviceIdentifier(), device.getEnrolmentInfo().getOwner(), device.getType()};
Object[] payload = new Object[]{
@ -299,10 +343,6 @@ public class DeviceInformationManagerImpl implements DeviceInformationManager {
} catch (DeviceManagementException e) {
DeviceManagementDAOFactory.rollbackTransaction();
throw new DeviceDetailsMgtException("Error occurred while getting the device information.", e);
} catch (DeviceManagementDAOException e) {
DeviceManagementDAOFactory.rollbackTransaction();
throw new DeviceDetailsMgtException("Error occurred while updating the last updated timestamp of " +
"the device", e);
} catch (DataPublisherConfigurationException e) {
DeviceManagementDAOFactory.rollbackTransaction();
throw new DeviceDetailsMgtException("Error occurred while publishing the device location information.", e);
@ -355,9 +395,13 @@ public class DeviceInformationManagerImpl implements DeviceInformationManager {
getDeviceManagementProvider().getAllDevices(deviceIdentifiers.get(0).getType(), false);
List<DeviceLocation> deviceLocations = new ArrayList<>();
DeviceManagementDAOFactory.openConnection();
DeviceLocation deviceLocation;
for (Device device : devices) {
deviceLocations.add(deviceDetailsDAO.getDeviceLocation(device.getId(),
device.getEnrolmentInfo().getId()));
deviceLocation = deviceDetailsDAO.getDeviceLocation(device.getId(),
device.getEnrolmentInfo().getId());
if (deviceLocation != null) {
deviceLocations.add(deviceLocation);
}
}
return deviceLocations;
} catch (DeviceManagementException e) {
@ -420,9 +464,6 @@ public class DeviceInformationManagerImpl implements DeviceInformationManager {
if (newDeviceInfo.getAvailableRAMMemory() == -1D) {
newDeviceInfo.setAvailableRAMMemory(previousDeviceInfo.getAvailableRAMMemory());
}
if (!newDeviceInfo.isPluggedIn()) {
newDeviceInfo.setPluggedIn(previousDeviceInfo.isPluggedIn());
}
Map<String, String> newDeviceDetailsMap = newDeviceInfo.getDeviceDetailsMap();
Map<String, String> previousDeviceDetailsMap = previousDeviceInfo.getDeviceDetailsMap();
for (String eachKey : previousDeviceDetailsMap.keySet()) {

@ -46,6 +46,8 @@ import org.wso2.carbon.device.mgt.core.config.datasource.DataSourceConfig;
import org.wso2.carbon.device.mgt.core.config.tenant.PlatformConfigurationManagementServiceImpl;
import org.wso2.carbon.device.mgt.core.dao.DeviceManagementDAOFactory;
import org.wso2.carbon.device.mgt.core.dao.GroupManagementDAOFactory;
import org.wso2.carbon.device.mgt.core.device.details.mgt.DeviceInformationManager;
import org.wso2.carbon.device.mgt.core.device.details.mgt.impl.DeviceInformationManagerImpl;
import org.wso2.carbon.device.mgt.core.geo.service.GeoLocationProviderServiceImpl;
import org.wso2.carbon.device.mgt.core.notification.mgt.NotificationManagementServiceImpl;
import org.wso2.carbon.device.mgt.core.notification.mgt.dao.NotificationManagementDAOFactory;
@ -57,6 +59,8 @@ import org.wso2.carbon.device.mgt.core.privacy.impl.PrivacyComplianceProviderImp
import org.wso2.carbon.device.mgt.core.push.notification.mgt.PushNotificationProviderRepository;
import org.wso2.carbon.device.mgt.core.push.notification.mgt.task.PushNotificationSchedulerTask;
import org.wso2.carbon.device.mgt.core.report.mgt.ReportManagementServiceImpl;
import org.wso2.carbon.device.mgt.core.search.mgt.SearchManagerService;
import org.wso2.carbon.device.mgt.core.search.mgt.impl.SearchManagerServiceImpl;
import org.wso2.carbon.device.mgt.core.service.DeviceManagementProviderService;
import org.wso2.carbon.device.mgt.core.service.DeviceManagementProviderServiceImpl;
import org.wso2.carbon.device.mgt.core.service.GroupManagementProviderService;
@ -325,6 +329,9 @@ public class DeviceManagementServiceComponent {
/* Registering PermissionManager Service */
PermissionManagerService permissionManagerService = PermissionManagerServiceImpl.getInstance();
bundleContext.registerService(PermissionManagerService.class.getName(), permissionManagerService, null);
bundleContext.registerService(DeviceInformationManager.class, new DeviceInformationManagerImpl(), null);
bundleContext.registerService(SearchManagerService.class, new SearchManagerServiceImpl(), null);
}
private void setupDeviceManagementSchema(DataSourceConfig config) throws DeviceManagementException {

@ -16,21 +16,17 @@
* under the License.
*/
package org.wso2.carbon.device.mgt.core.internal;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.osgi.framework.BundleContext;
import org.osgi.service.component.ComponentContext;
import org.wso2.carbon.device.mgt.common.DeviceStatusTaskPluginConfig;
import org.wso2.carbon.device.mgt.common.OperationMonitoringTaskConfig;
import org.wso2.carbon.device.mgt.core.config.DeviceConfigurationManager;
import org.wso2.carbon.device.mgt.core.config.DeviceManagementConfig;
import org.wso2.carbon.device.mgt.core.device.details.mgt.DeviceInformationManager;
import org.wso2.carbon.device.mgt.core.device.details.mgt.impl.DeviceInformationManagerImpl;
import org.wso2.carbon.device.mgt.core.dto.DeviceType;
import org.wso2.carbon.device.mgt.core.search.mgt.SearchManagerService;
import org.wso2.carbon.device.mgt.core.search.mgt.impl.SearchManagerServiceImpl;
import org.wso2.carbon.device.mgt.core.status.task.DeviceStatusTaskException;
import org.wso2.carbon.device.mgt.core.status.task.DeviceStatusTaskManagerService;
import org.wso2.carbon.device.mgt.core.status.task.impl.DeviceStatusTaskManagerServiceImpl;
@ -39,7 +35,6 @@ import org.wso2.carbon.device.mgt.core.task.DeviceTaskManagerService;
import org.wso2.carbon.device.mgt.core.task.impl.DeviceTaskManagerServiceImpl;
import org.wso2.carbon.ntask.core.service.TaskService;
import java.util.ArrayList;
import java.util.Map;
/**
@ -52,9 +47,11 @@ import java.util.Map;
* unbind="unsetTaskService"
*/
@SuppressWarnings("unused")
public class DeviceTaskManagerServiceComponent {
private static Log log = LogFactory.getLog(DeviceTaskManagerServiceComponent.class);
private DeviceManagementConfig deviceManagementConfig;
@SuppressWarnings("unused")
protected void activate(ComponentContext componentContext) {
@ -62,45 +59,40 @@ public class DeviceTaskManagerServiceComponent {
if (log.isDebugEnabled()) {
log.debug("Initializing device task manager bundle.");
}
getDeviceOperationMonitoringConfig(componentContext);
startOperationMonitoringTask(componentContext.getBundleContext());
//Start the DeviceStatusMonitoringTask for registered DeviceTypes
DeviceManagementConfig deviceManagementConfig = DeviceConfigurationManager.getInstance().
deviceManagementConfig = DeviceConfigurationManager.getInstance().
getDeviceManagementConfig();
if (deviceManagementConfig != null && deviceManagementConfig.getDeviceStatusTaskConfig().isEnabled()) {
startDeviceStatusMonitoringTask();
startDeviceStatusMonitoringTask(componentContext.getBundleContext());
}
componentContext.getBundleContext().registerService(DeviceInformationManager.class,
new DeviceInformationManagerImpl(), null);
componentContext.getBundleContext().registerService(SearchManagerService.class,
new SearchManagerServiceImpl(), null);
} catch (Throwable e) {
log.error("Error occurred while initializing device task manager service.", e);
}
}
private void getDeviceOperationMonitoringConfig(ComponentContext componentContext)
private void startOperationMonitoringTask(BundleContext bundleContext)
throws DeviceMgtTaskException {
DeviceTaskManagerService deviceTaskManagerService = new DeviceTaskManagerServiceImpl();
DeviceManagementDataHolder.getInstance().setDeviceTaskManagerService(deviceTaskManagerService);
componentContext.getBundleContext().registerService(DeviceTaskManagerService.class,
deviceTaskManagerService, null);
bundleContext.registerService(DeviceTaskManagerService.class, deviceTaskManagerService, null);
Map<String, OperationMonitoringTaskConfig> deviceConfigMap = DeviceMonitoringOperationDataHolder
.getInstance().getOperationMonitoringConfigFromMap();
for (String platformType : new ArrayList<>(deviceConfigMap.keySet())) {
if (deviceConfigMap.get(platformType).isEnabled()){
deviceTaskManagerService.startTask(platformType, deviceConfigMap.get(platformType));
for (String platformType : deviceConfigMap.keySet()) {
OperationMonitoringTaskConfig taskConfig = deviceConfigMap.get(platformType);
if (taskConfig.isEnabled()) {
deviceTaskManagerService.startTask(platformType, taskConfig);
}
deviceConfigMap.remove(platformType);
}
}
private void startDeviceStatusMonitoringTask() {
private void startDeviceStatusMonitoringTask(BundleContext bundleContext) {
DeviceStatusTaskManagerService deviceStatusTaskManagerService = new DeviceStatusTaskManagerServiceImpl();
DeviceManagementDataHolder.getInstance().setDeviceStatusTaskManagerService(deviceStatusTaskManagerService);
bundleContext.registerService(DeviceStatusTaskManagerService.class, deviceStatusTaskManagerService, null);
Map<DeviceType, DeviceStatusTaskPluginConfig> deviceStatusTaskPluginConfigs = DeviceManagementDataHolder.
getInstance().getDeviceStatusTaskPluginConfigs();
for (DeviceType deviceType : new ArrayList<>(deviceStatusTaskPluginConfigs.keySet())) {
for (DeviceType deviceType : deviceStatusTaskPluginConfigs.keySet()) {
try {
deviceStatusTaskManagerService.startTask(deviceType, deviceStatusTaskPluginConfigs.get(deviceType));
} catch (DeviceStatusTaskException e) {
@ -113,10 +105,41 @@ public class DeviceTaskManagerServiceComponent {
@SuppressWarnings("unused")
protected void deactivate(ComponentContext componentContext) {
try {
// DeviceTaskManagerService taskManagerService = new DeviceTaskManagerServiceImpl();
// taskManagerService.stopTask();
stopOperationMonitoringTask();
if (deviceManagementConfig != null && deviceManagementConfig.getDeviceStatusTaskConfig().isEnabled()) {
stopDeviceStatusMonitoringTask();
}
} catch (Throwable e) {
log.error("Error occurred while destroying the device details retrieving task manager service.", e);
log.error("Error occurred while shutting down device task manager service.", e);
}
}
private void stopOperationMonitoringTask()
throws DeviceMgtTaskException {
DeviceTaskManagerService deviceTaskManagerService = DeviceManagementDataHolder.getInstance()
.getDeviceTaskManagerService();
Map<String, OperationMonitoringTaskConfig> deviceConfigMap = DeviceMonitoringOperationDataHolder
.getInstance().getOperationMonitoringConfigFromMap();
for (String platformType : deviceConfigMap.keySet()) {
OperationMonitoringTaskConfig taskConfig = deviceConfigMap.get(platformType);
if (taskConfig.isEnabled()) {
deviceTaskManagerService.stopTask(platformType, taskConfig);
}
}
}
private void stopDeviceStatusMonitoringTask() {
DeviceStatusTaskManagerService deviceStatusTaskManagerService = DeviceManagementDataHolder.getInstance()
.getDeviceStatusTaskManagerService();
Map<DeviceType, DeviceStatusTaskPluginConfig> deviceStatusTaskPluginConfigs = DeviceManagementDataHolder.
getInstance().getDeviceStatusTaskPluginConfigs();
for (DeviceType deviceType : deviceStatusTaskPluginConfigs.keySet()) {
try {
deviceStatusTaskManagerService.stopTask(deviceType, deviceStatusTaskPluginConfigs.get(deviceType));
} catch (DeviceStatusTaskException e) {
log.error("Exception occurred while stopping the DeviceStatusMonitoring Task for deviceType '" +
deviceType + "'", e);
}
}
}
@ -133,4 +156,4 @@ public class DeviceTaskManagerServiceComponent {
}
DeviceManagementDataHolder.getInstance().setTaskService(null);
}
}
}

@ -196,7 +196,6 @@ public class OperationManagerImpl implements OperationManager {
operation.setInitiatedBy(initiatedBy);
}
OperationManagementDAOFactory.beginTransaction();
org.wso2.carbon.device.mgt.core.dto.operation.mgt.Operation operationDto = OperationDAOUtil
.convertOperation(operation);
int enrolmentId;
@ -209,6 +208,7 @@ public class OperationManagerImpl implements OperationManager {
authorizedDevices.add(device);
}
OperationManagementDAOFactory.beginTransaction();
if (operationDto.getControl()
== org.wso2.carbon.device.mgt.core.dto.operation.mgt.Operation.Control.NO_REPEAT) {
int existingOperationID;
@ -253,14 +253,14 @@ public class OperationManagerImpl implements OperationManager {
isScheduled = notificationStrategy.getConfig().isScheduled();
}
//TODO have to create a sql to load device details from deviceDAO using single query.
List<Integer> enrolmentIds = new ArrayList<>();
for (Device device : authorizedDevices) {
enrolmentId = device.getEnrolmentInfo().getId();
//Do not repeat the task operations
operationMappingDAO.addOperationMapping(operationId, enrolmentId, isScheduled);
enrolmentIds.add(enrolmentId);
}
operationMappingDAO.addOperationMapping(operationId, enrolmentIds, isScheduled);
OperationManagementDAOFactory.commitTransaction();
if (!isScheduled) {
if (!isScheduled && notificationStrategy != null) {
for (Device device : authorizedDevices) {
this.sendNotification(operation, device);
}
@ -319,7 +319,7 @@ public class OperationManagerImpl implements OperationManager {
.device.mgt.core.dto.operation.mgt.Operation.PushNotificationStatus.SCHEDULED);
OperationManagementDAOFactory.commitTransaction();
} catch (OperationManagementDAOException ex) {
// Not throwing this exception in order to keep sending remaining notifications if any.
// Not throwing this exception in order to keep scheduling remaining notifications if any.
log.error("Error occurred while setting push notification status to SCHEDULED.", ex);
OperationManagementDAOFactory.rollbackTransaction();
}
@ -501,13 +501,6 @@ public class OperationManagerImpl implements OperationManager {
List<Operation> operations = new ArrayList<>();
List<org.wso2.carbon.device.mgt.core.dto.operation.mgt.Operation> dtoOperationList = new ArrayList<>();
if (!isActionAuthorized(deviceId)) {
throw new OperationManagementException("User '" + getUser() + "' is not authorized to access the '" +
deviceId.getType() + "' device, which carries the identifier '" +
deviceId.getId() + "'");
}
//
EnrolmentInfo enrolmentInfo = this.getActiveEnrolmentInfo(deviceId);
if (enrolmentInfo == null) {
throw new OperationManagementException("Device not found for the given device Identifier:" +
@ -552,6 +545,28 @@ public class OperationManagerImpl implements OperationManager {
return operations;
}
@Override
public List<? extends Operation> getPendingOperations(Device device) throws OperationManagementException {
EnrolmentInfo enrolmentInfo = device.getEnrolmentInfo();
if (enrolmentInfo == null) {
throw new OperationManagementException("Device not found for the given device Identifier:" +
device.getId() + " and given type:" +
device.getType());
}
int enrolmentId = enrolmentInfo.getId();
//Changing the enrollment status & attempt count if the device is marked as inactive or unreachable
switch (enrolmentInfo.getStatus()) {
case INACTIVE:
case UNREACHABLE:
this.setEnrolmentStatus(enrolmentId, EnrolmentInfo.Status.ACTIVE);
break;
}
DeviceIdentifier deviceIdentifier = new DeviceIdentifier();
deviceIdentifier.setType(device.getType());
deviceIdentifier.setId(device.getDeviceIdentifier());
return getOperations(deviceIdentifier, Operation.Status.PENDING, enrolmentId);
}
@Override
public Operation getNextPendingOperation(DeviceIdentifier deviceId) throws OperationManagementException {
// setting notNowOperationFrequency to -1 to avoid picking notnow operations
@ -648,15 +663,8 @@ public class OperationManagerImpl implements OperationManager {
@Override
public void updateOperation(DeviceIdentifier deviceId, Operation operation) throws OperationManagementException {
int operationId = operation.getId();
if (log.isDebugEnabled()) {
log.debug("operation Id:" + operationId + " status:" + operation.getStatus());
}
if (!isActionAuthorized(deviceId)) {
throw new OperationManagementException("User '" + getUser() + "' is not authorized to access the '" +
deviceId.getType() + "' device, which carries the identifier '" +
deviceId.getId() + "'");
log.debug("operation Id:" + operation.getId() + " status:" + operation.getStatus());
}
EnrolmentInfo enrolmentInfo = this.getActiveEnrolmentInfo(deviceId);
@ -665,9 +673,13 @@ public class OperationManagerImpl implements OperationManager {
"Device not found for device id:" + deviceId.getId() + " " + "type:" +
deviceId.getType());
}
updateOperation(enrolmentInfo.getId(), operation);
}
@Override
public void updateOperation(int enrolmentId, Operation operation) throws OperationManagementException {
int operationId = operation.getId();
try {
int enrolmentId = enrolmentInfo.getId();
OperationManagementDAOFactory.beginTransaction();
if (operation.getStatus() != null) {
operationDAO.updateOperationStatus(enrolmentId, operationId,
@ -1165,4 +1177,41 @@ public class OperationManagerImpl implements OperationManager {
private boolean isSameUser(String user, String owner) {
return user.equalsIgnoreCase(owner);
}
private List<? extends Operation> getOperations(DeviceIdentifier deviceId, Operation.Status status, int enrolmentId)
throws OperationManagementException {
List<Operation> operations = new ArrayList<>();
List<org.wso2.carbon.device.mgt.core.dto.operation.mgt.Operation> dtoOperationList = new ArrayList<>();
org.wso2.carbon.device.mgt.core.dto.operation.mgt.Operation.Status internalStatus =
org.wso2.carbon.device.mgt.core.dto.operation.mgt.Operation.Status.valueOf(status.name());
try {
OperationManagementDAOFactory.openConnection();
dtoOperationList.addAll(commandOperationDAO.getOperationsByDeviceAndStatus(
enrolmentId, internalStatus));
dtoOperationList.addAll(configOperationDAO.getOperationsByDeviceAndStatus(
enrolmentId, internalStatus));
dtoOperationList.addAll(profileOperationDAO.getOperationsByDeviceAndStatus(
enrolmentId, internalStatus));
dtoOperationList.addAll(policyOperationDAO.getOperationsByDeviceAndStatus(
enrolmentId, internalStatus));
Operation operation;
for (org.wso2.carbon.device.mgt.core.dto.operation.mgt.Operation dtoOperation : dtoOperationList) {
operation = OperationDAOUtil.convertOperation(dtoOperation);
operations.add(operation);
}
operations.sort(new OperationIdComparator());
} catch (OperationManagementDAOException e) {
throw new OperationManagementException("Error occurred while retrieving the list of " +
"pending operations assigned for '" + deviceId.getType() +
"' device '" + deviceId.getId() + "'", e);
} catch (SQLException e) {
throw new OperationManagementException(
"Error occurred while opening a connection to the data source", e);
} finally {
OperationManagementDAOFactory.closeConnection();
}
return operations;
}
}

@ -18,7 +18,6 @@
*/
package org.wso2.carbon.device.mgt.core.operation.mgt.dao;
import org.wso2.carbon.device.mgt.common.DeviceIdentifier;
import org.wso2.carbon.device.mgt.core.dto.operation.mgt.Operation;
import org.wso2.carbon.device.mgt.core.operation.mgt.OperationEnrolmentMapping;
import org.wso2.carbon.device.mgt.core.operation.mgt.OperationMapping;
@ -28,7 +27,11 @@ import java.util.Map;
public interface OperationMappingDAO {
void addOperationMapping(int operationId, Integer deviceId, boolean isScheduled) throws OperationManagementDAOException;
void addOperationMapping(int operationId, int enrollmentId, boolean isScheduled)
throws OperationManagementDAOException;
void addOperationMapping(int operationId, List<Integer> enrollmentIds, boolean isScheduled)
throws OperationManagementDAOException;
void removeOperationMapping(int operationId, Integer deviceId) throws OperationManagementDAOException;

@ -28,29 +28,41 @@ import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Timestamp;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
public class CommandOperationDAOImpl extends GenericOperationDAOImpl {
@Override
public int addOperation(Operation operation) throws OperationManagementDAOException {
int operationId;
CommandOperation commandOp = (CommandOperation) operation;
PreparedStatement stmt = null;
ResultSet rs = null;
try {
operationId = super.addOperation(operation);
Connection conn = OperationManagementDAOFactory.getConnection();
stmt = conn.prepareStatement("INSERT INTO DM_COMMAND_OPERATION(OPERATION_ID, ENABLED) VALUES(?, ?)");
stmt.setInt(1, operationId);
stmt.setBoolean(2, commandOp.isEnabled());
Connection connection = OperationManagementDAOFactory.getConnection();
String sql = "INSERT INTO DM_OPERATION(TYPE, CREATED_TIMESTAMP, RECEIVED_TIMESTAMP, OPERATION_CODE, " +
"INITIATED_BY, ENABLED) VALUES (?, ?, ?, ?, ?, ?)";
stmt = connection.prepareStatement(sql, new String[]{"id"});
stmt.setString(1, operation.getType().toString());
stmt.setTimestamp(2, new Timestamp(new Date().getTime()));
stmt.setTimestamp(3, null);
stmt.setString(4, operation.getCode());
stmt.setString(5, operation.getInitiatedBy());
stmt.setBoolean(6, operation.isEnabled());
stmt.executeUpdate();
rs = stmt.getGeneratedKeys();
int id = -1;
if (rs.next()) {
id = rs.getInt(1);
}
return id;
} catch (SQLException e) {
throw new OperationManagementDAOException("Error occurred while adding command operation", e);
} finally {
OperationManagementDAOUtil.cleanupResources(stmt);
OperationManagementDAOUtil.cleanupResources(stmt, rs);
}
return operationId;
}
public CommandOperation getOperation(int id) throws OperationManagementDAOException {
@ -59,13 +71,14 @@ public class CommandOperationDAOImpl extends GenericOperationDAOImpl {
CommandOperation commandOperation = null;
try {
Connection conn = OperationManagementDAOFactory.getConnection();
String sql = "SELECT OPERATION_ID, ENABLED FROM DM_COMMAND_OPERATION WHERE OPERATION_ID = ?";
String sql = "SELECT ID, ENABLED FROM DM_OPERATION WHERE ID = ? AND TYPE='COMMAND'";
stmt = conn.prepareStatement(sql);
stmt.setInt(1, id);
rs = stmt.executeQuery();
if (rs.next()) {
commandOperation = new CommandOperation();
commandOperation.setId(rs.getInt("ID"));
commandOperation.setEnabled(rs.getBoolean("ENABLED"));
}
} catch (SQLException e) {
@ -87,11 +100,11 @@ public class CommandOperationDAOImpl extends GenericOperationDAOImpl {
List<CommandOperation> commandOperations = new ArrayList<>();
try {
Connection conn = OperationManagementDAOFactory.getConnection();
String sql = "SELECT o.ID, co1.ENABLED, co1.STATUS, o.TYPE, o.CREATED_TIMESTAMP, o.RECEIVED_TIMESTAMP, " +
"o.OPERATION_CODE FROM (SELECT co.OPERATION_ID, co.ENABLED, dm.STATUS " +
"FROM DM_COMMAND_OPERATION co INNER JOIN (SELECT ENROLMENT_ID, OPERATION_ID, STATUS " +
String sql = "SELECT co1.ID, co1.ENABLED, co1.STATUS, co1.TYPE, co1.CREATED_TIMESTAMP, co1.RECEIVED_TIMESTAMP, " +
"co1.OPERATION_CODE FROM (SELECT co.ID, co.TYPE, co.CREATED_TIMESTAMP, co.RECEIVED_TIMESTAMP, co.OPERATION_CODE, co.ENABLED, dm.STATUS " +
"FROM DM_OPERATION co INNER JOIN (SELECT ENROLMENT_ID, OPERATION_ID, STATUS " +
"FROM DM_ENROLMENT_OP_MAPPING WHERE ENROLMENT_ID = ? AND STATUS = ?) dm " +
"ON dm.OPERATION_ID = co.OPERATION_ID) co1 INNER JOIN DM_OPERATION o ON co1.OPERATION_ID = o.ID";
"ON dm.OPERATION_ID = co.ID and co.TYPE='COMMAND') co1";
stmt = conn.prepareStatement(sql);
stmt.setInt(1, enrolmentId);

@ -34,6 +34,7 @@ import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Timestamp;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
public class ConfigOperationDAOImpl extends GenericOperationDAOImpl {
@ -42,22 +43,33 @@ public class ConfigOperationDAOImpl extends GenericOperationDAOImpl {
@Override
public int addOperation(Operation operation) throws OperationManagementDAOException {
int operationId;
PreparedStatement stmt = null;
ResultSet rs = null;
try {
operationId = super.addOperation(operation);
operation.setCreatedTimeStamp(new Timestamp(new java.util.Date().getTime()).toString());
Connection conn = OperationManagementDAOFactory.getConnection();
stmt = conn.prepareStatement("INSERT INTO DM_CONFIG_OPERATION(OPERATION_ID, OPERATION_CONFIG) VALUES(?, ?)");
stmt.setInt(1, operationId);
stmt.setObject(2, operation);
Connection connection = OperationManagementDAOFactory.getConnection();
String sql = "INSERT INTO DM_OPERATION(TYPE, CREATED_TIMESTAMP, RECEIVED_TIMESTAMP, OPERATION_CODE, " +
"INITIATED_BY, OPERATION_DETAILS) VALUES (?, ?, ?, ?, ?, ?)";
stmt = connection.prepareStatement(sql, new String[]{"id"});
stmt.setString(1, operation.getType().toString());
stmt.setTimestamp(2, new Timestamp(new Date().getTime()));
stmt.setTimestamp(3, null);
stmt.setString(4, operation.getCode());
stmt.setString(5, operation.getInitiatedBy());
stmt.setObject(6, operation);
stmt.executeUpdate();
rs = stmt.getGeneratedKeys();
int id = -1;
if (rs.next()) {
id = rs.getInt(1);
}
return id;
} catch (SQLException e) {
throw new OperationManagementDAOException("Error occurred while adding command operation", e);
} finally {
OperationManagementDAOUtil.cleanupResources(stmt);
OperationManagementDAOUtil.cleanupResources(stmt, rs);
}
return operationId;
}
@Override
@ -70,17 +82,17 @@ public class ConfigOperationDAOImpl extends GenericOperationDAOImpl {
ObjectInputStream ois;
try {
Connection conn = OperationManagementDAOFactory.getConnection();
String sql = "SELECT OPERATION_ID, ENABLED, OPERATION_CONFIG FROM DM_CONFIG_OPERATION WHERE OPERATION_ID = ?";
String sql = "SELECT ID, ENABLED, OPERATION_DETAILS FROM DM_OPERATION WHERE ID = ? AND TYPE='CONFIG'";
stmt = conn.prepareStatement(sql);
stmt.setInt(1, operationId);
rs = stmt.executeQuery();
if (rs.next()) {
byte[] operationDetails = rs.getBytes("OPERATION_CONFIG");
byte[] operationDetails = rs.getBytes("OPERATION_DETAILS");
bais = new ByteArrayInputStream(operationDetails);
ois = new ObjectInputStream(bais);
configOperation = (ConfigOperation) ois.readObject();
configOperation.setId(rs.getInt("OPERATION_ID"));
configOperation.setId(rs.getInt("ID"));
configOperation.setEnabled(rs.getBoolean("ENABLED"));
}
} catch (IOException e) {
@ -111,9 +123,9 @@ public class ConfigOperationDAOImpl extends GenericOperationDAOImpl {
ObjectInputStream ois = null;
try {
Connection conn = OperationManagementDAOFactory.getConnection();
String sql = "SELECT co.OPERATION_ID, co.OPERATION_CONFIG FROM DM_CONFIG_OPERATION co " +
String sql = "SELECT co.ID, co.OPERATION_DETAILS FROM DM_OPERATION co " +
"INNER JOIN (SELECT * FROM DM_ENROLMENT_OP_MAPPING WHERE ENROLMENT_ID = ? " +
"AND STATUS = ?) dm ON dm.OPERATION_ID = co.OPERATION_ID";
"AND STATUS = ?) dm ON dm.OPERATION_ID = co.ID WHERE co.TYPE = 'CONFIG'";
stmt = conn.prepareStatement(sql);
stmt.setInt(1, enrolmentId);
@ -121,12 +133,12 @@ public class ConfigOperationDAOImpl extends GenericOperationDAOImpl {
rs = stmt.executeQuery();
while (rs.next()) {
byte[] operationDetails = rs.getBytes("OPERATION_CONFIG");
byte[] operationDetails = rs.getBytes("OPERATION_DETAILS");
bais = new ByteArrayInputStream(operationDetails);
ois = new ObjectInputStream(bais);
configOperation = (ConfigOperation) ois.readObject();
configOperation.setStatus(status);
configOperation.setId(rs.getInt("OPERATION_ID"));
configOperation.setId(rs.getInt("ID"));
operations.add(configOperation);
}
} catch (IOException e) {

@ -64,13 +64,14 @@ public class GenericOperationDAOImpl implements OperationDAO {
try {
Connection connection = OperationManagementDAOFactory.getConnection();
String sql = "INSERT INTO DM_OPERATION(TYPE, CREATED_TIMESTAMP, RECEIVED_TIMESTAMP, OPERATION_CODE, " +
"INITIATED_BY) VALUES (?, ?, ?, ?, ?)";
"INITIATED_BY, OPERATION_DETAILS) VALUES (?, ?, ?, ?, ?, ?)";
stmt = connection.prepareStatement(sql, new String[]{"id"});
stmt.setString(1, operation.getType().toString());
stmt.setTimestamp(2, new Timestamp(new Date().getTime()));
stmt.setTimestamp(3, null);
stmt.setString(4, operation.getCode());
stmt.setString(5, operation.getInitiatedBy());
stmt.setObject(6, operation);
stmt.executeUpdate();
rs = stmt.getGeneratedKeys();

@ -39,7 +39,7 @@ import java.util.Map;
public class OperationMappingDAOImpl implements OperationMappingDAO {
@Override
public void addOperationMapping(int operationId, Integer deviceId, boolean isScheduled) throws
public void addOperationMapping(int operationId, int enrollmentId, boolean isScheduled) throws
OperationManagementDAOException {
PreparedStatement stmt = null;
try {
@ -48,7 +48,7 @@ public class OperationMappingDAOImpl implements OperationMappingDAO {
String sql = "INSERT INTO DM_ENROLMENT_OP_MAPPING(ENROLMENT_ID, OPERATION_ID, STATUS, " +
"PUSH_NOTIFICATION_STATUS, CREATED_TIMESTAMP, UPDATED_TIMESTAMP) VALUES (?, ?, ?, ?, ?, ?)";
stmt = conn.prepareStatement(sql);
stmt.setInt(1, deviceId);
stmt.setInt(1, enrollmentId);
stmt.setInt(2, operationId);
stmt.setString(3, Operation.Status.PENDING.toString());
if (isScheduled) {
@ -66,6 +66,37 @@ public class OperationMappingDAOImpl implements OperationMappingDAO {
}
}
@Override
public void addOperationMapping(int operationId, List<Integer> enrollmentIds, boolean isScheduled) throws
OperationManagementDAOException {
PreparedStatement stmt = null;
try {
long time = System.currentTimeMillis() / 1000;
Connection conn = OperationManagementDAOFactory.getConnection();
String sql = "INSERT INTO DM_ENROLMENT_OP_MAPPING(ENROLMENT_ID, OPERATION_ID, STATUS, " +
"PUSH_NOTIFICATION_STATUS, CREATED_TIMESTAMP, UPDATED_TIMESTAMP) VALUES (?, ?, ?, ?, ?, ?)";
stmt = conn.prepareStatement(sql);
for (int enrollmentId : enrollmentIds) {
stmt.setInt(1, enrollmentId);
stmt.setInt(2, operationId);
stmt.setString(3, Operation.Status.PENDING.toString());
if (isScheduled) {
stmt.setString(4, Operation.PushNotificationStatus.SCHEDULED.toString());
} else {
stmt.setString(4, Operation.PushNotificationStatus.COMPLETED.toString());
}
stmt.setLong(5, time);
stmt.setLong(6, time);
stmt.addBatch();
}
stmt.executeBatch();
} catch (SQLException e) {
throw new OperationManagementDAOException("Error occurred while persisting device operation mappings", e);
} finally {
OperationManagementDAOUtil.cleanupResources(stmt, null);
}
}
@Override
public void removeOperationMapping(int operationId,
Integer deviceId) throws OperationManagementDAOException {

@ -29,6 +29,7 @@ import org.wso2.carbon.device.mgt.core.operation.mgt.dao.OperationManagementDAOU
import java.io.*;
import java.sql.*;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
public class PolicyOperationDAOImpl extends GenericOperationDAOImpl {
@ -37,27 +38,38 @@ public class PolicyOperationDAOImpl extends GenericOperationDAOImpl {
@Override
public int addOperation(Operation operation) throws OperationManagementDAOException {
int operationId;
PreparedStatement stmt = null;
ResultSet rs = null;
ByteArrayOutputStream bao = null;
ObjectOutputStream oos = null;
int operationId = -1;
try {
operationId = super.addOperation(operation);
operation.setCreatedTimeStamp(new Timestamp(new java.util.Date().getTime()).toString());
operation.setId(operationId);
operation.setEnabled(true);
PolicyOperation policyOperation = (PolicyOperation) operation;
Connection conn = OperationManagementDAOFactory.getConnection();
stmt = conn.prepareStatement("INSERT INTO DM_POLICY_OPERATION(OPERATION_ID, OPERATION_DETAILS) " +
"VALUES(?, ?)");
Connection connection = OperationManagementDAOFactory.getConnection();
String sql = "INSERT INTO DM_OPERATION(TYPE, CREATED_TIMESTAMP, RECEIVED_TIMESTAMP, OPERATION_CODE, " +
"INITIATED_BY, OPERATION_DETAILS, ENABLED) VALUES (?, ?, ?, ?, ?, ?, ?)";
stmt = connection.prepareStatement(sql, new String[]{"id"});
stmt.setString(1, operation.getType().toString());
stmt.setTimestamp(2, new Timestamp(new Date().getTime()));
stmt.setTimestamp(3, null);
stmt.setString(4, operation.getCode());
stmt.setString(5, operation.getInitiatedBy());
bao = new ByteArrayOutputStream();
oos = new ObjectOutputStream(bao);
oos.writeObject(operation);
stmt.setInt(1, operationId);
stmt.setBytes(2, bao.toByteArray());
stmt.setObject(6, operation);
stmt.setBoolean(7, operation.isEnabled());
stmt.executeUpdate();
rs = stmt.getGeneratedKeys();
if (rs.next()) {
operationId = rs.getInt(1);
}
return operationId;
} catch (SQLException e) {
throw new OperationManagementDAOException("Error occurred while adding policy operation", e);
} catch (IOException e) {
@ -77,9 +89,8 @@ public class PolicyOperationDAOImpl extends GenericOperationDAOImpl {
log.warn("Error occurred while closing ObjectOutputStream", e);
}
}
OperationManagementDAOUtil.cleanupResources(stmt);
OperationManagementDAOUtil.cleanupResources(stmt, rs);
}
return operationId;
}
@Override
@ -92,7 +103,7 @@ public class PolicyOperationDAOImpl extends GenericOperationDAOImpl {
ObjectInputStream ois;
try {
Connection conn = OperationManagementDAOFactory.getConnection();
String sql = "SELECT OPERATION_ID, ENABLED, OPERATION_DETAILS FROM DM_POLICY_OPERATION WHERE OPERATION_ID=?";
String sql = "SELECT ID, ENABLED, OPERATION_DETAILS FROM DM_OPERATION WHERE ID=? AND TYPE='POLICY'";
stmt = conn.prepareStatement(sql);
stmt.setInt(1, operationId);
rs = stmt.executeQuery();
@ -102,6 +113,7 @@ public class PolicyOperationDAOImpl extends GenericOperationDAOImpl {
bais = new ByteArrayInputStream(operationDetails);
ois = new ObjectInputStream(bais);
policyOperation = (PolicyOperation) ois.readObject();
policyOperation.setId(rs.getInt("ID"));
}
} catch (IOException e) {
throw new OperationManagementDAOException("IO Error occurred while de serialize the policy operation " +
@ -130,9 +142,9 @@ public class PolicyOperationDAOImpl extends GenericOperationDAOImpl {
ObjectInputStream ois = null;
try {
Connection conn = OperationManagementDAOFactory.getConnection();
String sql = "SELECT po.OPERATION_ID, ENABLED, OPERATION_DETAILS FROM DM_POLICY_OPERATION po " +
String sql = "SELECT po.ID, ENABLED, OPERATION_DETAILS FROM DM_OPERATION po " +
"INNER JOIN (SELECT * FROM DM_ENROLMENT_OP_MAPPING WHERE ENROLMENT_ID = ? " +
"AND STATUS = ?) dm ON dm.OPERATION_ID = po.OPERATION_ID";
"AND STATUS = ?) dm ON dm.OPERATION_ID = po.ID WHERE po.TYPE='POLICY'";
stmt = conn.prepareStatement(sql);
stmt.setInt(1, enrolmentId);
@ -145,6 +157,7 @@ public class PolicyOperationDAOImpl extends GenericOperationDAOImpl {
ois = new ObjectInputStream(bais);
policyOperation = (PolicyOperation) ois.readObject();
policyOperation.setStatus(status);
policyOperation.setId(rs.getInt("ID"));
operations.add(policyOperation);
}
} catch (IOException e) {

@ -29,6 +29,7 @@ import org.wso2.carbon.device.mgt.core.operation.mgt.dao.OperationManagementDAOU
import java.io.*;
import java.sql.*;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
public class ProfileOperationDAOImpl extends GenericOperationDAOImpl {
@ -37,27 +38,36 @@ public class ProfileOperationDAOImpl extends GenericOperationDAOImpl {
public int addOperation(Operation operation) throws OperationManagementDAOException {
PreparedStatement stmt = null;
ResultSet rs = null;
ByteArrayOutputStream bao = null;
ObjectOutputStream oos = null;
int operationId;
try {
operationId = super.addOperation(operation);
operation.setCreatedTimeStamp(new Timestamp(new java.util.Date().getTime()).toString());
operation.setId(operationId);
operation.setEnabled(true);
//ProfileOperation profileOp = (ProfileOperation) operation;
Connection conn = OperationManagementDAOFactory.getConnection();
stmt = conn.prepareStatement("INSERT INTO DM_PROFILE_OPERATION(OPERATION_ID, OPERATION_DETAILS) " +
"VALUES(?, ?)");
Connection connection = OperationManagementDAOFactory.getConnection();
String sql = "INSERT INTO DM_OPERATION(TYPE, CREATED_TIMESTAMP, RECEIVED_TIMESTAMP, OPERATION_CODE, " +
"INITIATED_BY, OPERATION_DETAILS, ENABLED) VALUES (?, ?, ?, ?, ?, ?, ?)";
stmt = connection.prepareStatement(sql, new String[]{"id"});
stmt.setString(1, operation.getType().toString());
stmt.setTimestamp(2, new Timestamp(new Date().getTime()));
stmt.setTimestamp(3, null);
stmt.setString(4, operation.getCode());
stmt.setString(5, operation.getInitiatedBy());
bao = new ByteArrayOutputStream();
oos = new ObjectOutputStream(bao);
oos.writeObject(operation.getPayLoad());
stmt.setInt(1, operationId);
stmt.setBytes(2, bao.toByteArray());
stmt.setBytes(6, bao.toByteArray());
stmt.setBoolean(7, operation.isEnabled());
stmt.executeUpdate();
rs = stmt.getGeneratedKeys();
int id = -1;
if (rs.next()) {
id = rs.getInt(1);
}
return id;
} catch (SQLException e) {
throw new OperationManagementDAOException("Error occurred while adding profile operation", e);
} catch (IOException e) {
@ -79,7 +89,6 @@ public class ProfileOperationDAOImpl extends GenericOperationDAOImpl {
}
OperationManagementDAOUtil.cleanupResources(stmt);
}
return operationId;
}
public Operation getOperation(int id) throws OperationManagementDAOException {
@ -91,9 +100,8 @@ public class ProfileOperationDAOImpl extends GenericOperationDAOImpl {
ObjectInputStream ois;
try {
Connection conn = OperationManagementDAOFactory.getConnection();
String sql = "SELECT o.ID, po.ENABLED, po.OPERATION_DETAILS, o.CREATED_TIMESTAMP, o.OPERATION_CODE " +
"FROM DM_PROFILE_OPERATION po INNER JOIN DM_OPERATION o ON po.OPERATION_ID = o.ID WHERE po" +
".OPERATION_ID=?";
String sql = "SELECT po.ID, po.ENABLED, po.OPERATION_DETAILS, po.CREATED_TIMESTAMP, po.OPERATION_CODE " +
"FROM DM_OPERATION po WHERE po.ID=? AND po.TYPE='PROFILE'";
stmt = conn.prepareStatement(sql);
stmt.setInt(1, id);
@ -114,6 +122,9 @@ public class ProfileOperationDAOImpl extends GenericOperationDAOImpl {
profileOperation.setPayLoad(obj);
} else {
profileOperation = (ProfileOperation) obj;
profileOperation.setCode(rs.getString("OPERATION_CODE"));
profileOperation.setId(rs.getInt("ID"));
profileOperation.setCreatedTimeStamp(rs.getString("CREATED_TIMESTAMP"));
}
}
} catch (IOException e) {
@ -145,12 +156,11 @@ public class ProfileOperationDAOImpl extends GenericOperationDAOImpl {
try {
Connection conn = OperationManagementDAOFactory.getConnection();
String sql = "SELECT o.ID, po1.ENABLED, po1.STATUS, o.TYPE, o.CREATED_TIMESTAMP, o.RECEIVED_TIMESTAMP, " +
"o.OPERATION_CODE, po1.OPERATION_DETAILS " +
"FROM (SELECT po.OPERATION_ID, po.ENABLED, po.OPERATION_DETAILS, dm.STATUS " +
"FROM DM_PROFILE_OPERATION po INNER JOIN (SELECT ENROLMENT_ID, OPERATION_ID, STATUS FROM DM_ENROLMENT_OP_MAPPING " +
"WHERE ENROLMENT_ID = ? AND STATUS = ?) dm ON dm.OPERATION_ID = po.OPERATION_ID) po1 " +
"INNER JOIN DM_OPERATION o ON po1.OPERATION_ID = o.ID ";
String sql = "SELECT po1.ID, po1.ENABLED, po1.STATUS, po1.TYPE, po1.CREATED_TIMESTAMP, po1.RECEIVED_TIMESTAMP, " +
"po1.OPERATION_CODE, po1.OPERATION_DETAILS " +
"FROM (SELECT po.ID, po.ENABLED, po.OPERATION_DETAILS, po.TYPE, po.OPERATION_CODE, po.CREATED_TIMESTAMP, po.RECEIVED_TIMESTAMP, dm.STATUS " +
"FROM DM_OPERATION po INNER JOIN (SELECT ENROLMENT_ID, OPERATION_ID, STATUS FROM DM_ENROLMENT_OP_MAPPING " +
"WHERE ENROLMENT_ID = ? AND STATUS = ?) dm ON dm.OPERATION_ID = po.ID WHERE po.TYPE='PROFILE') po1";
stmt = conn.prepareStatement(sql);
stmt.setInt(1, enrolmentId);
@ -174,6 +184,9 @@ public class ProfileOperationDAOImpl extends GenericOperationDAOImpl {
} else {
profileOperation = (ProfileOperation) obj;
profileOperation.setStatus(status);
profileOperation.setCode(rs.getString("OPERATION_CODE"));
profileOperation.setId(rs.getInt("ID"));
profileOperation.setCreatedTimeStamp(rs.getString("CREATED_TIMESTAMP"));
operationList.add(profileOperation);
}
}

@ -43,40 +43,6 @@ import java.util.List;
*/
public class MySQLOperationDAOImpl extends GenericOperationDAOImpl {
@Override
public boolean updateOperationStatus(int enrolmentId, int operationId, Operation.Status status)
throws OperationManagementDAOException {
PreparedStatement stmt = null;
boolean isUpdated = false;
try {
long time = System.currentTimeMillis() / 1000;
Connection connection = OperationManagementDAOFactory.getConnection();
stmt = connection.prepareStatement("SELECT STATUS, UPDATED_TIMESTAMP FROM DM_ENROLMENT_OP_MAPPING " +
"WHERE ENROLMENT_ID=? and OPERATION_ID=? FOR UPDATE");
stmt.setString(1, status.toString());
stmt.setLong(2, time);
if (stmt.execute()) {
OperationManagementDAOUtil.cleanupResources(stmt);
stmt = connection.prepareStatement("UPDATE DM_ENROLMENT_OP_MAPPING SET STATUS=?, UPDATED_TIMESTAMP=? " +
"WHERE ENROLMENT_ID=? and OPERATION_ID=?");
stmt.setString(1, status.toString());
stmt.setLong(2, time);
stmt.setInt(3, enrolmentId);
stmt.setInt(4, operationId);
int numOfRecordsUpdated = stmt.executeUpdate();
if (numOfRecordsUpdated != 0) {
isUpdated = true;
}
}
} catch (SQLException e) {
throw new OperationManagementDAOException("Error occurred while update device mapping operation status " +
"metadata", e);
} finally {
OperationManagementDAOUtil.cleanupResources(stmt);
}
return isUpdated;
}
@Override
public List<Activity> getActivityList(List<Integer> activityIds) throws OperationManagementDAOException {
PreparedStatement stmt = null;

@ -215,6 +215,48 @@ public class ReportManagementServiceImpl implements ReportManagementService {
}
}
@Override
public PaginationResult getDevicesByEncryptionStatus(PaginationRequest request, boolean isEncrypted)
throws ReportManagementException {
if (request == null) {
String msg = "Error. The request must be a not null value.";
log.error(msg);
throw new ReportManagementException(msg);
}
try {
int tenantId = DeviceManagementDAOUtil.getTenantId();
PaginationResult paginationResult = new PaginationResult();
DeviceManagerUtil.validateDeviceListPageSize(request);
try {
DeviceManagementDAOFactory.openConnection();
List<Device> devices = deviceDAO.getDevicesByEncryptionStatus(request, tenantId, isEncrypted);
int deviceCount = deviceDAO.getCountOfDevicesByEncryptionStatus(tenantId, isEncrypted);
paginationResult.setData(devices);
paginationResult.setRecordsFiltered(devices.size());
paginationResult.setRecordsTotal(deviceCount);
return paginationResult;
} catch (SQLException e) {
String msg = "Error occurred while opening a connection to the data source";
log.error(msg, e);
throw new ReportManagementException(msg, e);
} finally {
DeviceManagementDAOFactory.closeConnection();
}
} catch (DeviceManagementDAOException e) {
String msg = "Error occurred while retrieving expired devices by encryption status for the tenant";
log.error(msg, e);
throw new ReportManagementException(msg, e);
} catch (DeviceManagementException e) {
String msg = "Error occurred while validating the request";
log.error(msg, e);
throw new ReportManagementException(msg, e);
}
}
//NOTE: This is just a temporary method for retrieving device counts
public JsonObject buildCount(String start, String end, List<Count> countList) throws ParseException {
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd");

@ -21,6 +21,7 @@ package org.wso2.carbon.device.mgt.core.search.mgt.impl;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.wso2.carbon.context.CarbonContext;
import org.wso2.carbon.device.mgt.common.Device;
import org.wso2.carbon.device.mgt.common.DeviceIdentifier;
import org.wso2.carbon.device.mgt.common.DeviceManagementConstants;
@ -210,9 +211,10 @@ public class ProcessorImpl implements Processor {
private void setApplicationListOfDevices(List<Device> devices) throws SearchMgtException {
try {
DeviceManagementDAOFactory.openConnection();
int tenantId = CarbonContext.getThreadLocalCarbonContext().getTenantId();
for (Device device : devices) {
device.setApplications(applicationDAO.getInstalledApplications(device.getId(),
device.getEnrolmentInfo().getId()));
device.getEnrolmentInfo().getId(), tenantId));
}
} catch (DeviceManagementDAOException e) {
throw new SearchMgtException("Error occurred while fetching the Application List of devices ", e);

@ -656,16 +656,23 @@ public interface DeviceManagementProviderService {
PaginationResult getOperations(DeviceIdentifier deviceId,
PaginationRequest request) throws OperationManagementException;
@Deprecated
List<? extends Operation> getPendingOperations(
DeviceIdentifier deviceId) throws OperationManagementException;
List<? extends Operation> getPendingOperations(
Device device) throws OperationManagementException;
Operation getNextPendingOperation(DeviceIdentifier deviceId) throws OperationManagementException;
Operation getNextPendingOperation(DeviceIdentifier deviceId, long notNowOperationFrequency)
throws OperationManagementException;
@Deprecated
void updateOperation(DeviceIdentifier deviceId, Operation operation) throws OperationManagementException;
void updateOperation(Device device, Operation operation) throws OperationManagementException;
boolean updateProperties(DeviceIdentifier deviceId, List<Device.Property> properties) throws DeviceManagementException;
Operation getOperationByDeviceAndOperationId(DeviceIdentifier deviceId, int operationId)
@ -875,4 +882,6 @@ public interface DeviceManagementProviderService {
* @throws ApplicationManagementException if any service level or DAO level error occurs.
*/
List<String> getAppVersions(String packageName) throws ApplicationManagementException;
int getFunctioningDevicesInSystem() throws DeviceManagementException;
}

@ -116,6 +116,7 @@ import org.wso2.carbon.device.mgt.core.dao.DeviceManagementDAOFactory;
import org.wso2.carbon.device.mgt.core.dao.DeviceTypeDAO;
import org.wso2.carbon.device.mgt.core.dao.EnrollmentDAO;
import org.wso2.carbon.device.mgt.core.dao.util.DeviceManagementDAOUtil;
import org.wso2.carbon.device.mgt.core.device.details.mgt.DeviceDetailsMgtException;
import org.wso2.carbon.device.mgt.core.device.details.mgt.DeviceInformationManager;
import org.wso2.carbon.device.mgt.core.device.details.mgt.dao.DeviceDetailsDAO;
import org.wso2.carbon.device.mgt.core.device.details.mgt.dao.DeviceDetailsMgtDAOException;
@ -169,9 +170,11 @@ public class DeviceManagementProviderServiceImpl implements DeviceManagementProv
private EnrollmentDAO enrollmentDAO;
private ApplicationDAO applicationDAO;
private DeviceManagementPluginRepository pluginRepository;
private DeviceInformationManager deviceInformationManager;
public DeviceManagementProviderServiceImpl() {
this.pluginRepository = new DeviceManagementPluginRepository();
this.deviceInformationManager = new DeviceInformationManagerImpl();
initDataAccessObjects();
/* Registering a listener to retrieve events when some device management service plugin is installed after
* the component is done getting initialized */
@ -386,6 +389,16 @@ public class DeviceManagementProviderServiceImpl implements DeviceManagementProv
sendNotification(device);
}
extractDeviceLocationToUpdate(device);
try {
if (device.getDeviceInfo() != null) {
deviceInformationManager.addDeviceInfo(device, device.getDeviceInfo());
}
} catch (DeviceDetailsMgtException e) {
//This is not logging as error, neither throwing an exception as this is not an exception in main
// business logic.
String msg = "Error occurred while adding device info";
log.warn(msg, e);
}
return status;
}
@ -1817,6 +1830,12 @@ public class DeviceManagementProviderServiceImpl implements DeviceManagementProv
.getPendingOperations(deviceId);
}
@Override
public List<? extends Operation> getPendingOperations(Device device) throws OperationManagementException {
return pluginRepository.getOperationManager(device.getType(), this.getTenantId())
.getPendingOperations(device);
}
@Override
public Operation getNextPendingOperation(DeviceIdentifier deviceId) throws OperationManagementException {
// // setting notNowOperationFrequency to -1 to avoid picking notnow operations
@ -1864,6 +1883,46 @@ public class DeviceManagementProviderServiceImpl implements DeviceManagementProv
}
}
@Override
public void updateOperation(Device device, Operation operation) throws OperationManagementException {
EnrolmentInfo enrolmentInfo = device.getEnrolmentInfo();
if (enrolmentInfo == null) {
throw new OperationManagementException(
"Device not found for device id:" + device.getDeviceIdentifier() + " " + "type:" +
device.getType());
}
pluginRepository.getOperationManager(device.getType(), this.getTenantId())
.updateOperation(enrolmentInfo.getId(), operation);
try {
if (DeviceManagerUtil.isPublishOperationResponseEnabled()) {
List<String> permittedOperations = DeviceManagerUtil.getEnabledOperationsForResponsePublish();
if (permittedOperations.contains(operation.getCode())
|| permittedOperations.contains("*")) {
Object[] metaData = {device.getDeviceIdentifier(), device.getType()};
Object[] payload = new Object[]{
Calendar.getInstance().getTimeInMillis(),
operation.getId(),
operation.getCode(),
operation.getType() != null ? operation.getType().toString() : null,
operation.getStatus() != null ? operation.getStatus().toString() : null,
operation.getOperationResponse()
};
DeviceManagerUtil.getEventPublisherService().publishEvent(
OPERATION_RESPONSE_EVENT_STREAM_DEFINITION, "1.0.0", metaData, new Object[0], payload
);
}
}
} catch (DeviceManagementException e) {
String msg = "Error occurred while reading configs.";
log.error(msg, e);
throw new OperationManagementException(msg, e);
} catch (DataPublisherConfigurationException e) {
String msg = "Error occurred while publishing event.";
log.error(msg, e);
throw new OperationManagementException(msg, e);
}
}
@Override
public boolean updateProperties(DeviceIdentifier deviceId, List<Device.Property> properties)
throws DeviceManagementException {
@ -3062,7 +3121,9 @@ public class DeviceManagementProviderServiceImpl implements DeviceManagementProv
List<Application> applications;
try {
DeviceManagementDAOFactory.openConnection();
applications = applicationDAO.getInstalledApplications(device.getId(), device.getEnrolmentInfo().getId());
int tenantId = CarbonContext.getThreadLocalCarbonContext().getTenantId();
applications = applicationDAO.getInstalledApplications(device.getId(),
device.getEnrolmentInfo().getId(), tenantId);
device.setApplications(applications);
} catch (DeviceManagementDAOException e) {
String msg = "Error occurred while retrieving the application list of '" + device.getType() + "', " +
@ -3366,8 +3427,7 @@ public class DeviceManagementProviderServiceImpl implements DeviceManagementProv
deviceLocation.setDistance(Double.parseDouble(distance));
deviceLocation.setSpeed(Float.parseFloat(speed));
deviceLocation.setBearing(Float.parseFloat(bearing));
DeviceInformationManager deviceInformationManager = new DeviceInformationManagerImpl();
deviceInformationManager.addDeviceLocation(deviceLocation);
deviceInformationManager.addDeviceLocation(device, deviceLocation);
} catch (Exception e) {
//We are not failing the execution since this is not critical for the functionality. But logging as
// a warning for reference.
@ -4060,4 +4120,28 @@ public class DeviceManagementProviderServiceImpl implements DeviceManagementProv
deviceConfiguration.setDeviceOwner(deviceOwner);
return deviceConfiguration;
}
public int getFunctioningDevicesInSystem() throws DeviceManagementException {
if (log.isDebugEnabled()) {
log.debug("Get functioning devices count");
}
try {
DeviceManagementDAOFactory.openConnection();
return deviceDAO.getFunctioningDevicesInSystem();
} catch (DeviceManagementDAOException e) {
String msg = "Error occurred while retrieving the device count";
log.error(msg, e);
throw new DeviceManagementException(msg, e);
} catch (SQLException e) {
String msg = "Error occurred while opening a connection to the data source";
log.error(msg, e);
throw new DeviceManagementException(msg, e);
} catch (Exception e) {
String msg = "Error occurred in getDeviceCount";
log.error(msg, e);
throw new DeviceManagementException(msg, e);
} finally {
DeviceManagementDAOFactory.closeConnection();
}
}
}

@ -100,7 +100,7 @@ public class DeviceStatusTaskManagerServiceImpl implements DeviceStatusTaskManag
try {
TaskService taskService = DeviceManagementDataHolder.getInstance().getTaskService();
String taskName = DEVICE_STATUS_MONITORING_TASK_TYPE + "_" + deviceType.getName() + "_" + deviceType.getId();
if (taskService.isServerInit()) {
if (taskService != null && taskService.isServerInit()) {
TaskManager taskManager = taskService.getTaskManager(DEVICE_STATUS_MONITORING_TASK_TYPE);
taskManager.deleteTask(taskName);
}

@ -119,12 +119,18 @@ public class DeviceTaskManagerImpl implements DeviceTaskManager {
DeviceManagementProviderService deviceManagementProviderService = DeviceManagementDataHolder.getInstance().
getDeviceManagementProvider();
try {
List<Device> devices;
List<String> operations;
//list operations for device type
List<String> operations = this.getValidOperationNames();
if (operations.isEmpty()) {
if (log.isDebugEnabled()) {
log.debug("No operations are available.");
}
return;
}
List<DeviceIdentifier> validDeviceIdentifiers;
List<String> startupOperations;
operations = this.getValidOperationNames(); //list operations for each device type
devices = deviceManagementProviderService.getAllDevices(deviceType, false);//list devices for each type
//list devices of device type
List<Device> devices = deviceManagementProviderService.getAllDevices(deviceType, false);
if (!devices.isEmpty()) {
if (log.isDebugEnabled() && deviceType != null) {
@ -150,7 +156,7 @@ public class DeviceTaskManagerImpl implements DeviceTaskManager {
}
} else {
if (log.isDebugEnabled()) {
log.debug("No operations are available.");
log.debug("No valid devices are available.");
}
}
} else {

@ -109,9 +109,9 @@ public class DeviceTaskManagerServiceImpl implements DeviceTaskManagerService {
try {
int tenantId = PrivilegedCarbonContext.getThreadLocalCarbonContext().getTenantId();
TaskService taskService = DeviceManagementDataHolder.getInstance().getTaskService();
if (taskService.isServerInit()) {
if (taskService != null && taskService.isServerInit()) {
TaskManager taskManager = taskService.getTaskManager(TASK_TYPE);
String taskName = deviceType + String.valueOf(tenantId);
String taskName = deviceType + tenantId;
taskManager.deleteTask(taskName);
}
} catch (TaskException e) {
@ -133,7 +133,7 @@ public class DeviceTaskManagerServiceImpl implements DeviceTaskManagerService {
TaskManager taskManager = taskService.getTaskManager(TASK_TYPE);
if (taskManager.isTaskScheduled(deviceType)) {
String taskName = deviceType + String.valueOf(tenantId);
String taskName = deviceType + tenantId;
taskManager.deleteTask(taskName);
TaskInfo.TriggerInfo triggerInfo = new TaskInfo.TriggerInfo();
triggerInfo.setIntervalMillis(operationMonitoringTaskConfig.getFrequency());

@ -1,85 +0,0 @@
/*
* Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
*
* WSO2 Inc. licenses this file to you under the Apache License,
* Version 2.0 (the "License"); you may not use this file except
* in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*
*/
package org.wso2.carbon.device.mgt.core.dao;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.testng.Assert;
import org.testng.annotations.BeforeClass;
import org.testng.annotations.Test;
import org.wso2.carbon.device.mgt.common.app.mgt.Application;
import org.wso2.carbon.device.mgt.core.common.BaseDeviceManagementTest;
import org.wso2.carbon.device.mgt.core.common.TestDataHolder;
import java.sql.SQLException;
public class ApplicationPersistenceTests extends BaseDeviceManagementTest {
private static final Log log = LogFactory.getLog(ApplicationPersistenceTests.class);
private ApplicationDAO applicationDAO = null;
@Test
public void testAddApplication() {
/* Adding dummy application to the application store */
String testAppIdentifier = "test sample1";
try {
DeviceManagementDAOFactory.openConnection();
applicationDAO.addApplication(TestDataHolder.generateApplicationDummyData(testAppIdentifier), -1234);
} catch (DeviceManagementDAOException | SQLException e) {
log.error("Error occurred while adding application test sample1", e);
} finally {
DeviceManagementDAOFactory.closeConnection();
}
/* Retrieving the application by its name */
Application target = null;
try {
target = this.getApplication(testAppIdentifier, -1234);
} catch (DeviceManagementDAOException e) {
String msg = "Error occurred while retrieving application info";
log.error(msg, e);
Assert.fail(msg, e);
}
if (!isMock()) {
Assert.assertEquals(target.getApplicationIdentifier(), testAppIdentifier,
"Application added is not as same as what's retrieved");
}
}
private Application getApplication(String appIdentifier, int tenantId) throws DeviceManagementDAOException {
Application application = null;
try {
DeviceManagementDAOFactory.openConnection();
application = applicationDAO.getApplication(appIdentifier, tenantId);
} catch (SQLException e) {
log.error("Error occurred while metadata corresponding to the application '" + appIdentifier + "'", e);
} finally {
DeviceManagementDAOFactory.closeConnection();
}
return application;
}
@BeforeClass
@Override
public void init() throws Exception {
this.initDataSource();
applicationDAO = DeviceManagementDAOFactory.getApplicationDAO();
}
}

@ -266,19 +266,6 @@ public class OperationManagementTests extends BaseDeviceManagementTest {
}
}
@Test(dependsOnMethods = "getOperations", expectedExceptions = OperationManagementException.class)
public void getPendingOperationsAsNonAdmin() throws DeviceManagementException, OperationManagementException,
InvalidDeviceException {
try {
startTenantFlowAsNonAdmin();
for (DeviceIdentifier deviceIdentifier : deviceIds) {
this.operationMgtService.getPendingOperations(deviceIdentifier);
}
} finally {
PrivilegedCarbonContext.endTenantFlow();
}
}
@Test(dependsOnMethods = "getPendingOperations")
public void getPaginatedRequestAsAdmin() throws OperationManagementException {
PrivilegedCarbonContext.startTenantFlow();
@ -339,7 +326,7 @@ public class OperationManagementTests extends BaseDeviceManagementTest {
Assert.assertEquals(pendingOperations.size(), 3);
}
@Test(dependsOnMethods = "updateOperation", expectedExceptions = OperationManagementException.class)
@Test(dependsOnMethods = "updateOperation")
public void updateOperationAsNonAdmin() throws OperationManagementException {
//This is required to introduce a delay for the update operation of the device.
try {
@ -356,7 +343,7 @@ public class OperationManagementTests extends BaseDeviceManagementTest {
operation.setOperationResponse("The operation is successfully completed, and updated by non admin!");
this.operationMgtService.updateOperation(deviceIdentifier, operation);
List pendingOperations = this.operationMgtService.getPendingOperations(deviceIdentifier);
Assert.assertEquals(pendingOperations.size(), 3);
Assert.assertEquals(pendingOperations.size(), 2);
} finally {
PrivilegedCarbonContext.endTenantFlow();
}
@ -442,7 +429,7 @@ public class OperationManagementTests extends BaseDeviceManagementTest {
DeviceIdentifier deviceIdentifier = this.deviceIds.get(0);
List operation = this.operationMgtService.getOperationsByDeviceAndStatus(deviceIdentifier,
Operation.Status.PENDING);
Assert.assertEquals(operation.size(), 2);
Assert.assertEquals(operation.size(), 1);
}
@Test(dependsOnMethods = "getOperationByDeviceAndOperationId", expectedExceptions = OperationManagementException.class)
@ -515,8 +502,8 @@ public class OperationManagementTests extends BaseDeviceManagementTest {
public void getActivityCountUpdatedAfter() throws OperationManagementException, ParseException {
int activityCount = this.operationMgtService.getActivityCountUpdatedAfter
(this.commandActivityBeforeUpdatedTimestamp / 1000);
Assert.assertTrue(activityCount == 2,
"The activities updated after the created should be 2");
Assert.assertEquals(activityCount, 3,
"The activities updated after the created should be 3");
}
@Test

@ -88,7 +88,7 @@ public class ProcessorImplTest extends BaseDeviceManagementTest {
context.setConditions(conditions);
ProcessorImpl processor = new ProcessorImpl();
List<Device> devices = processor.execute(context);
Assert.assertEquals(5, devices.size(), "There should be exactly 5 devices with matching search criteria");
Assert.assertEquals(devices.size(), 5, "There should be exactly 5 devices with matching search criteria");
}
@Test (description = "Search for device with or condition")
@ -106,7 +106,7 @@ public class ProcessorImplTest extends BaseDeviceManagementTest {
context.setConditions(conditions);
ProcessorImpl processor = new ProcessorImpl();
List<Device> devices = processor.execute(context);
Assert.assertEquals(5, devices.size(), "There should be exactly 5 devices with matching search criteria");
Assert.assertEquals(devices.size(), 5, "There should be exactly 5 devices with matching search criteria");
}
@Test (description = "Search for device with wrong condition")

@ -31,7 +31,6 @@
<class name="org.wso2.carbon.device.mgt.core.DeviceManagementRepositoryTests"/>
<class name="org.wso2.carbon.device.mgt.core.DeviceManagementConfigTests"/>
<class name="org.wso2.carbon.device.mgt.core.app.mgt.AppManagementConfigurationManagerTest"/>
<class name="org.wso2.carbon.device.mgt.core.dao.ApplicationPersistenceTests"/>
<class name="org.wso2.carbon.device.mgt.core.search.DeviceDetails"/>
<class name="org.wso2.carbon.device.mgt.core.dao.GroupPersistTests"/>
</classes>

@ -31,7 +31,6 @@
<class name="org.wso2.carbon.device.mgt.core.DeviceManagementRepositoryTests"/>
<class name="org.wso2.carbon.device.mgt.core.DeviceManagementConfigTests"/>
<class name="org.wso2.carbon.device.mgt.core.app.mgt.AppManagementConfigurationManagerTest"/>
<class name="org.wso2.carbon.device.mgt.core.dao.ApplicationPersistenceTests"/>
<class name="org.wso2.carbon.device.mgt.core.search.DeviceDetails"/>
<class name="org.wso2.carbon.device.mgt.core.dao.GroupPersistTests"/>
</classes>

@ -31,7 +31,6 @@
<class name="org.wso2.carbon.device.mgt.core.DeviceManagementRepositoryTests"/>
<class name="org.wso2.carbon.device.mgt.core.DeviceManagementConfigTests"/>
<class name="org.wso2.carbon.device.mgt.core.app.mgt.AppManagementConfigurationManagerTest"/>
<class name="org.wso2.carbon.device.mgt.core.dao.ApplicationPersistenceTests"/>
<class name="org.wso2.carbon.device.mgt.core.search.DeviceDetails"/>
<class name="org.wso2.carbon.device.mgt.core.dao.GroupPersistTests"/>
</classes>

@ -31,7 +31,6 @@
<class name="org.wso2.carbon.device.mgt.core.DeviceManagementRepositoryTests"/>
<class name="org.wso2.carbon.device.mgt.core.DeviceManagementConfigTests"/>
<class name="org.wso2.carbon.device.mgt.core.app.mgt.AppManagementConfigurationManagerTest"/>
<class name="org.wso2.carbon.device.mgt.core.dao.ApplicationPersistenceTests"/>
<class name="org.wso2.carbon.device.mgt.core.search.DeviceDetails"/>
<class name="org.wso2.carbon.device.mgt.core.dao.GroupPersistTests"/>
</classes>

@ -78,42 +78,9 @@ CREATE TABLE IF NOT EXISTS DM_OPERATION (
RECEIVED_TIMESTAMP TIMESTAMP NULL,
OPERATION_CODE VARCHAR(1000) NOT NULL,
INITIATED_BY VARCHAR(100) NULL,
PRIMARY KEY (ID)
);
CREATE TABLE IF NOT EXISTS DM_CONFIG_OPERATION (
OPERATION_ID INTEGER NOT NULL,
OPERATION_CONFIG BLOB DEFAULT NULL,
ENABLED BOOLEAN NOT NULL DEFAULT FALSE,
PRIMARY KEY (OPERATION_ID),
CONSTRAINT fk_dm_operation_config FOREIGN KEY (OPERATION_ID) REFERENCES
DM_OPERATION (ID) ON DELETE NO ACTION ON UPDATE NO ACTION
);
CREATE TABLE IF NOT EXISTS DM_COMMAND_OPERATION (
OPERATION_ID INTEGER NOT NULL,
ENABLED BOOLEAN NOT NULL DEFAULT FALSE,
PRIMARY KEY (OPERATION_ID),
CONSTRAINT fk_dm_operation_command FOREIGN KEY (OPERATION_ID) REFERENCES
DM_OPERATION (ID) ON DELETE NO ACTION ON UPDATE NO ACTION
);
CREATE TABLE IF NOT EXISTS DM_POLICY_OPERATION (
OPERATION_ID INTEGER NOT NULL,
ENABLED INTEGER NOT NULL DEFAULT 0,
OPERATION_DETAILS BLOB DEFAULT NULL,
PRIMARY KEY (OPERATION_ID),
CONSTRAINT fk_dm_operation_policy FOREIGN KEY (OPERATION_ID) REFERENCES
DM_OPERATION (ID) ON DELETE NO ACTION ON UPDATE NO ACTION
);
CREATE TABLE IF NOT EXISTS DM_PROFILE_OPERATION (
OPERATION_ID INTEGER NOT NULL,
ENABLED INTEGER NOT NULL DEFAULT 0,
OPERATION_DETAILS BLOB DEFAULT NULL,
PRIMARY KEY (OPERATION_ID),
CONSTRAINT fk_dm_operation_profile FOREIGN KEY (OPERATION_ID) REFERENCES
DM_OPERATION (ID) ON DELETE NO ACTION ON UPDATE NO ACTION
ENABLED BOOLEAN NOT NULL DEFAULT FALSE,
PRIMARY KEY (ID)
);
CREATE TABLE IF NOT EXISTS DM_ENROLMENT (
@ -369,19 +336,8 @@ CREATE TABLE IF NOT EXISTS DM_APPLICATION (
APP_PROPERTIES BLOB NULL,
MEMORY_USAGE INTEGER(10) NULL,
IS_ACTIVE BOOLEAN NOT NULL DEFAULT FALSE,
TENANT_ID INTEGER NOT NULL,
PRIMARY KEY (ID)
);
CREATE TABLE IF NOT EXISTS DM_DEVICE_APPLICATION_MAPPING (
ID INTEGER AUTO_INCREMENT NOT NULL,
DEVICE_ID INTEGER NOT NULL,
ENROLMENT_ID INTEGER NOT NULL,
APPLICATION_ID INTEGER NOT NULL,
APP_PROPERTIES BLOB NULL,
MEMORY_USAGE INTEGER(10) NULL,
IS_ACTIVE BOOLEAN NOT NULL DEFAULT FALSE,
TENANT_ID INTEGER NOT NULL,
PRIMARY KEY (ID),
CONSTRAINT fk_dm_device
@ -389,11 +345,6 @@ CREATE TABLE IF NOT EXISTS DM_DEVICE_APPLICATION_MAPPING (
REFERENCES DM_DEVICE (ID)
ON DELETE NO ACTION
ON UPDATE NO ACTION,
CONSTRAINT fk_dm_application
FOREIGN KEY (APPLICATION_ID)
REFERENCES DM_APPLICATION (ID)
ON DELETE NO ACTION
ON UPDATE NO ACTION,
CONSTRAINT FK_DM_APP_MAP_DM_ENROL
FOREIGN KEY (ENROLMENT_ID)
REFERENCES DM_ENROLMENT (ID)

@ -31,7 +31,6 @@
<class name="org.wso2.carbon.device.mgt.core.DeviceManagementRepositoryTests"/>
<class name="org.wso2.carbon.device.mgt.core.DeviceManagementConfigTests"/>
<class name="org.wso2.carbon.device.mgt.core.app.mgt.AppManagementConfigurationManagerTest"/>
<class name="org.wso2.carbon.device.mgt.core.dao.ApplicationPersistenceTests"/>
<class name="org.wso2.carbon.device.mgt.core.search.DeviceDetails"/>
<class name="org.wso2.carbon.device.mgt.core.dao.GroupPersistTests"/>
</classes>

@ -183,7 +183,7 @@ public class DeviceTypeManagerService implements DeviceManagementService {
PlatformConfiguration deviceTypeConfig = deviceManager.getConfiguration();
if (deviceTypeConfig != null) {
List<ConfigurationEntry> configuration = deviceTypeConfig.getConfiguration();
if (!configuration.isEmpty()) {
if (configuration != null && !configuration.isEmpty()) {
Map<String, String> properties = this.getConfigProperty(configuration);
String notifierValue = properties.get(NOTIFIER_PROPERTY);
String enabledNotifierType = notifierType;

@ -34,7 +34,7 @@ public class SimpleEvaluationImpl implements SimpleEvaluation {
private static final Log log = LogFactory.getLog(SimpleEvaluationImpl.class);
private PolicyManagerService policyManagerService;
private List<Policy> policyList = new ArrayList<Policy>();
private volatile List<Policy> policyList = new ArrayList<Policy>();
@Override
public Policy getEffectivePolicy(DeviceIdentifier deviceIdentifier) throws PolicyEvaluationException {
@ -71,7 +71,7 @@ public class SimpleEvaluationImpl implements SimpleEvaluation {
}
@Override
public void sortPolicies() throws PolicyEvaluationException {
public synchronized void sortPolicies() throws PolicyEvaluationException {
Collections.sort(policyList);
}

@ -85,45 +85,9 @@ CREATE TABLE IF NOT EXISTS DM_OPERATION (
RECEIVED_TIMESTAMP TIMESTAMP NULL,
OPERATION_CODE VARCHAR(1000) NOT NULL,
INITIATED_BY VARCHAR(100) NULL,
PRIMARY KEY (ID)
);
DROP TABLE IF EXISTS DM_CONFIG_OPERATION;
CREATE TABLE IF NOT EXISTS DM_CONFIG_OPERATION (
OPERATION_ID INTEGER NOT NULL,
OPERATION_CONFIG BLOB DEFAULT NULL,
PRIMARY KEY (OPERATION_ID),
CONSTRAINT fk_dm_operation_config FOREIGN KEY (OPERATION_ID) REFERENCES
DM_OPERATION (ID) ON DELETE NO ACTION ON UPDATE NO ACTION
);
DROP TABLE IF EXISTS DM_COMMAND_OPERATION;
CREATE TABLE IF NOT EXISTS DM_COMMAND_OPERATION (
OPERATION_ID INTEGER NOT NULL,
ENABLED BOOLEAN NOT NULL DEFAULT FALSE,
PRIMARY KEY (OPERATION_ID),
CONSTRAINT fk_dm_operation_command FOREIGN KEY (OPERATION_ID) REFERENCES
DM_OPERATION (ID) ON DELETE NO ACTION ON UPDATE NO ACTION
);
DROP TABLE IF EXISTS DM_POLICY_OPERATION;
CREATE TABLE IF NOT EXISTS DM_POLICY_OPERATION (
OPERATION_ID INTEGER NOT NULL,
ENABLED INTEGER NOT NULL DEFAULT 0,
OPERATION_DETAILS BLOB DEFAULT NULL,
PRIMARY KEY (OPERATION_ID),
CONSTRAINT fk_dm_operation_policy FOREIGN KEY (OPERATION_ID) REFERENCES
DM_OPERATION (ID) ON DELETE NO ACTION ON UPDATE NO ACTION
);
DROP TABLE IF EXISTS DM_PROFILE_OPERATION;
CREATE TABLE IF NOT EXISTS DM_PROFILE_OPERATION (
OPERATION_ID INTEGER NOT NULL,
ENABLED INTEGER NOT NULL DEFAULT 0,
OPERATION_DETAILS BLOB DEFAULT NULL,
PRIMARY KEY (OPERATION_ID),
CONSTRAINT fk_dm_operation_profile FOREIGN KEY (OPERATION_ID) REFERENCES
DM_OPERATION (ID) ON DELETE NO ACTION ON UPDATE NO ACTION
ENABLED BOOLEAN NOT NULL DEFAULT FALSE,
PRIMARY KEY (ID)
);
DROP TABLE IF EXISTS DM_ENROLMENT;
@ -433,20 +397,8 @@ CREATE TABLE IF NOT EXISTS DM_APPLICATION (
APP_PROPERTIES BLOB NULL,
MEMORY_USAGE INTEGER(10) NULL,
IS_ACTIVE BOOLEAN NOT NULL DEFAULT FALSE,
TENANT_ID INTEGER NOT NULL,
PRIMARY KEY (ID)
);
DROP TABLE IF EXISTS DM_DEVICE_APPLICATION_MAPPING;
CREATE TABLE IF NOT EXISTS DM_DEVICE_APPLICATION_MAPPING (
ID INTEGER AUTO_INCREMENT NOT NULL,
DEVICE_ID INTEGER NOT NULL,
ENROLMENT_ID INTEGER NOT NULL,
APPLICATION_ID INTEGER NOT NULL,
APP_PROPERTIES BLOB NULL,
MEMORY_USAGE INTEGER(10) NULL,
IS_ACTIVE BOOLEAN NOT NULL DEFAULT FALSE,
TENANT_ID INTEGER NOT NULL,
PRIMARY KEY (ID),
CONSTRAINT fk_dm_device
@ -454,11 +406,6 @@ CREATE TABLE IF NOT EXISTS DM_DEVICE_APPLICATION_MAPPING (
REFERENCES DM_DEVICE (ID)
ON DELETE NO ACTION
ON UPDATE NO ACTION,
CONSTRAINT fk_dm_application
FOREIGN KEY (APPLICATION_ID)
REFERENCES DM_APPLICATION (ID)
ON DELETE NO ACTION
ON UPDATE NO ACTION,
CONSTRAINT FK_DM_APP_MAP_DM_ENROL
FOREIGN KEY (ENROLMENT_ID)
REFERENCES DM_ENROLMENT (ID)

@ -5,6 +5,9 @@ CREATE TABLE IF NOT EXISTS DM_OPERATION_ARCH (
CREATED_TIMESTAMP TIMESTAMP NOT NULL,
RECEIVED_TIMESTAMP TIMESTAMP NULL,
OPERATION_CODE VARCHAR(50) NOT NULL,
INITIATED_BY VARCHAR(100) NULL,
OPERATION_DETAILS BLOB DEFAULT NULL,
ENABLED BOOLEAN NOT NULL DEFAULT FALSE,
ARCHIVED_AT TIMESTAMP DEFAULT NOW(),
PRIMARY KEY (ID)
)ENGINE = InnoDB;
@ -15,19 +18,16 @@ CREATE TABLE IF NOT EXISTS DM_ENROLMENT_OP_MAPPING_ARCH (
ENROLMENT_ID INTEGER NOT NULL,
OPERATION_ID INTEGER NOT NULL,
STATUS VARCHAR(50) NULL,
PUSH_NOTIFICATION_STATUS VARCHAR(50) NULL,
CREATED_TIMESTAMP INTEGER NOT NULL,
UPDATED_TIMESTAMP INTEGER NOT NULL,
ARCHIVED_AT TIMESTAMP DEFAULT NOW(),
PRIMARY KEY (ID)
)ENGINE = InnoDB;
CREATE TABLE IF NOT EXISTS DM_DEVICE_OPERATION_RESPONSE_ARCH (
ID INT(11) NOT NULL,
ENROLMENT_ID INTEGER NOT NULL,
OPERATION_ID INTEGER NOT NULL,
EN_OP_MAP_ID INTEGER NOT NULL,
OPERATION_RESPONSE LONGBLOB DEFAULT NULL,
RECEIVED_TIMESTAMP TIMESTAMP NULL,
ARCHIVED_AT TIMESTAMP DEFAULT NOW(),
@ -44,26 +44,3 @@ CREATE TABLE IF NOT EXISTS DM_NOTIFICATION_ARCH (
ARCHIVED_AT TIMESTAMP DEFAULT NOW(),
PRIMARY KEY (NOTIFICATION_ID)
)ENGINE = InnoDB;
CREATE TABLE IF NOT EXISTS DM_COMMAND_OPERATION_ARCH (
OPERATION_ID INTEGER NOT NULL,
ENABLED BOOLEAN NOT NULL DEFAULT FALSE,
ARCHIVED_AT TIMESTAMP DEFAULT NOW(),
PRIMARY KEY (OPERATION_ID)
)ENGINE = InnoDB;
CREATE TABLE IF NOT EXISTS DM_CONFIG_OPERATION_ARCH (
OPERATION_ID INTEGER NOT NULL,
OPERATION_CONFIG BLOB DEFAULT NULL,
ENABLED BOOLEAN NOT NULL DEFAULT FALSE,
ARCHIVED_AT TIMESTAMP DEFAULT NOW(),
PRIMARY KEY (OPERATION_ID)
)ENGINE = InnoDB;
CREATE TABLE IF NOT EXISTS DM_PROFILE_OPERATION_ARCH (
OPERATION_ID INTEGER NOT NULL,
ENABLED INTEGER NOT NULL DEFAULT 0,
OPERATION_DETAILS BLOB DEFAULT NULL,
ARCHIVED_AT TIMESTAMP DEFAULT NOW(),
PRIMARY KEY (OPERATION_ID)
)ENGINE = InnoDB;

@ -87,42 +87,9 @@ CREATE TABLE IF NOT EXISTS DM_OPERATION (
RECEIVED_TIMESTAMP TIMESTAMP NULL,
OPERATION_CODE VARCHAR(1000) NOT NULL,
INITIATED_BY VARCHAR(100) NULL,
PRIMARY KEY (ID)
);
CREATE TABLE IF NOT EXISTS DM_CONFIG_OPERATION (
OPERATION_ID INTEGER NOT NULL,
OPERATION_CONFIG BLOB DEFAULT NULL,
ENABLED BOOLEAN NOT NULL DEFAULT FALSE,
PRIMARY KEY (OPERATION_ID),
CONSTRAINT fk_dm_operation_config FOREIGN KEY (OPERATION_ID) REFERENCES
DM_OPERATION (ID) ON DELETE NO ACTION ON UPDATE NO ACTION
);
CREATE TABLE IF NOT EXISTS DM_COMMAND_OPERATION (
OPERATION_ID INTEGER NOT NULL,
ENABLED BOOLEAN NOT NULL DEFAULT FALSE,
PRIMARY KEY (OPERATION_ID),
CONSTRAINT fk_dm_operation_command FOREIGN KEY (OPERATION_ID) REFERENCES
DM_OPERATION (ID) ON DELETE NO ACTION ON UPDATE NO ACTION
);
CREATE TABLE IF NOT EXISTS DM_POLICY_OPERATION (
OPERATION_ID INTEGER NOT NULL,
ENABLED INTEGER NOT NULL DEFAULT 0,
OPERATION_DETAILS BLOB DEFAULT NULL,
PRIMARY KEY (OPERATION_ID),
CONSTRAINT fk_dm_operation_policy FOREIGN KEY (OPERATION_ID) REFERENCES
DM_OPERATION (ID) ON DELETE NO ACTION ON UPDATE NO ACTION
);
CREATE TABLE IF NOT EXISTS DM_PROFILE_OPERATION (
OPERATION_ID INTEGER NOT NULL,
ENABLED INTEGER NOT NULL DEFAULT 0,
OPERATION_DETAILS BLOB DEFAULT NULL,
PRIMARY KEY (OPERATION_ID),
CONSTRAINT fk_dm_operation_profile FOREIGN KEY (OPERATION_ID) REFERENCES
DM_OPERATION (ID) ON DELETE NO ACTION ON UPDATE NO ACTION
ENABLED BOOLEAN NOT NULL DEFAULT FALSE,
PRIMARY KEY (ID)
);
CREATE TABLE IF NOT EXISTS DM_ENROLMENT (
@ -392,18 +359,8 @@ CREATE TABLE IF NOT EXISTS DM_APPLICATION (
APP_PROPERTIES BLOB NULL,
MEMORY_USAGE INTEGER(10) NULL,
IS_ACTIVE BOOLEAN NOT NULL DEFAULT FALSE,
TENANT_ID INTEGER NOT NULL,
PRIMARY KEY (ID)
);
CREATE TABLE IF NOT EXISTS DM_DEVICE_APPLICATION_MAPPING (
ID INTEGER AUTO_INCREMENT NOT NULL,
DEVICE_ID INTEGER NOT NULL,
ENROLMENT_ID INTEGER NOT NULL,
APPLICATION_ID INTEGER NOT NULL,
APP_PROPERTIES BLOB NULL,
MEMORY_USAGE INTEGER(10) NULL,
IS_ACTIVE BOOLEAN NOT NULL DEFAULT FALSE,
TENANT_ID INTEGER NOT NULL,
PRIMARY KEY (ID),
CONSTRAINT fk_dm_device
@ -411,11 +368,6 @@ CREATE TABLE IF NOT EXISTS DM_DEVICE_APPLICATION_MAPPING (
REFERENCES DM_DEVICE (ID)
ON DELETE NO ACTION
ON UPDATE NO ACTION,
CONSTRAINT fk_dm_application
FOREIGN KEY (APPLICATION_ID)
REFERENCES DM_APPLICATION (ID)
ON DELETE NO ACTION
ON UPDATE NO ACTION,
CONSTRAINT FK_DM_APP_MAP_DM_ENROL
FOREIGN KEY (ENROLMENT_ID)
REFERENCES DM_ENROLMENT (ID)

@ -102,42 +102,9 @@ CREATE TABLE IF NOT EXISTS DM_OPERATION (
RECEIVED_TIMESTAMP TIMESTAMP NULL,
OPERATION_CODE VARCHAR(50) NOT NULL,
INITIATED_BY VARCHAR(100) NULL,
PRIMARY KEY (ID)
)ENGINE = InnoDB;
CREATE TABLE IF NOT EXISTS DM_CONFIG_OPERATION (
OPERATION_ID INTEGER NOT NULL,
OPERATION_CONFIG BLOB DEFAULT NULL,
ENABLED BOOLEAN NOT NULL DEFAULT FALSE,
PRIMARY KEY (OPERATION_ID),
CONSTRAINT FK_DM_OPERATION_CONFIG FOREIGN KEY (OPERATION_ID) REFERENCES
DM_OPERATION (ID) ON DELETE NO ACTION ON UPDATE NO ACTION
)ENGINE = InnoDB;
CREATE TABLE IF NOT EXISTS DM_COMMAND_OPERATION (
OPERATION_ID INTEGER NOT NULL,
ENABLED BOOLEAN NOT NULL DEFAULT FALSE,
PRIMARY KEY (OPERATION_ID),
CONSTRAINT FK_DM_OPERATION_COMMAND FOREIGN KEY (OPERATION_ID) REFERENCES
DM_OPERATION (ID) ON DELETE NO ACTION ON UPDATE NO ACTION
)ENGINE = InnoDB;
CREATE TABLE IF NOT EXISTS DM_POLICY_OPERATION (
OPERATION_ID INTEGER NOT NULL,
ENABLED INTEGER NOT NULL DEFAULT 0,
OPERATION_DETAILS BLOB DEFAULT NULL,
PRIMARY KEY (OPERATION_ID),
CONSTRAINT FK_DM_OPERATION_POLICY FOREIGN KEY (OPERATION_ID) REFERENCES
DM_OPERATION (ID) ON DELETE NO ACTION ON UPDATE NO ACTION
)ENGINE = InnoDB;
CREATE TABLE IF NOT EXISTS DM_PROFILE_OPERATION (
OPERATION_ID INTEGER NOT NULL,
ENABLED INTEGER NOT NULL DEFAULT 0,
OPERATION_DETAILS BLOB DEFAULT NULL,
PRIMARY KEY (OPERATION_ID),
CONSTRAINT FK_DM_OPERATION_PROFILE FOREIGN KEY (OPERATION_ID) REFERENCES
DM_OPERATION (ID) ON DELETE NO ACTION ON UPDATE NO ACTION
ENABLED BOOLEAN NOT NULL DEFAULT FALSE,
PRIMARY KEY (ID)
)ENGINE = InnoDB;
CREATE TABLE IF NOT EXISTS DM_ENROLMENT (
@ -699,4 +666,4 @@ CREATE TABLE IF NOT EXISTS DM_ARCHIVED_OPERATIONS (
ID INTEGER NOT NULL,
CREATED_TIMESTAMP TIMESTAMP NOT NULL,
PRIMARY KEY (ID)
)ENGINE = InnoDB;
)ENGINE = InnoDB;

Loading…
Cancel
Save