use of org.eclipse.kapua.KapuaIllegalAccessException in project kapua by eclipse.
the class KapuaSecurityBrokerFilter method addExternalConnection.
private void addExternalConnection(ConnectionContext context, ConnectionInfo info) throws Exception {
// Clean-up credentials possibly associated with the current thread by previous connection.
ThreadContext.unbindSubject();
Context loginTotalContext = metricLoginAddConnectionTime.time();
String username = info.getUserName();
String password = info.getPassword();
String clientId = info.getClientId();
String clientIp = info.getClientIp();
ConnectionId connectionId = info.getConnectionId();
List<String> authDestinations = null;
if (logger.isDebugEnabled()) {
authDestinations = new ArrayList<>();
}
try {
// Build KapuaUsername
// User username = User.parse(username);//KapuaUserName
logger.info("User name {} - client id {}", new Object[] { username, clientId });
Context loginPreCheckTimeContext = metricLoginPreCheckTime.time();
// 1) validate client id
// Check the device Mqtt ClientId
// TODO move to deviceservice
// MqttUtils.checkDeviceClientId(clientId);
loginPreCheckTimeContext.stop();
Context loginShiroLoginTimeContext = metricLoginShiroLoginTime.time();
AuthenticationCredentials credentials = credentialsFactory.newInstance(username, password.toCharArray());
AccessToken accessToken = authenticationService.login(credentials);
KapuaId scopeId = accessToken.getScopeId();
KapuaId userId = accessToken.getUserId();
final Account account;
try {
account = KapuaSecurityUtils.doPriviledge(() -> accountService.find(scopeId));
} catch (Exception e) {
// to preserve the original exception message (if possible)
if (e instanceof AuthenticationException) {
throw (AuthenticationException) e;
} else {
throw new ShiroException("Error while find account!", e);
}
}
String accountName = account.getName();
loginShiroLoginTimeContext.stop();
// if a user acts as a child MOVED INSIDE KapuaAuthorizingRealm otherwise through REST API and console this @accountName won't work
// get account id and name from kapua session methods that check for the run as
//
// String accountName = kapuaSession.getSessionAccountName();
// long accountId = kapuaSession.getSessionAccountId();
// multiple account stealing link fix
String fullClientId = MessageFormat.format(AclConstants.MULTI_ACCOUNT_CLIENT_ID, scopeId.getId().longValue(), clientId);
KapuaPrincipal principal = new KapuaPrincipalImpl(accessToken, username, clientId, clientIp);
DeviceConnection deviceConnection = null;
// 3) check authorization
DefaultAuthorizationMap authMap = null;
if (isAdminUser(username)) {
metricLoginKapuasysTokenAttempt.inc();
// 3-1) admin authMap
authMap = buildAdminAuthMap(authDestinations, principal, fullClientId);
metricClientConnectedKapuasys.inc();
} else {
Context loginNormalUserTimeContext = metricLoginNormalUserTime.time();
metricLoginNormalUserAttempt.inc();
// 3-3) check permissions
Context loginCheckAccessTimeContext = metricLoginCheckAccessTime.time();
boolean[] hasPermissions = new boolean[] { // TODO check the permissions... move them to a constants class?
authorizationService.isPermitted(permissionFactory.newPermission(DeviceLifecycleDomain.DEVICE_LIFECYCLE, Actions.connect, scopeId)), authorizationService.isPermitted(permissionFactory.newPermission(DeviceManagementDomain.DEVICE_MANAGEMENT, Actions.write, scopeId)), authorizationService.isPermitted(permissionFactory.newPermission(DatastoreDomain.DATA_STORE, Actions.read, scopeId)), authorizationService.isPermitted(permissionFactory.newPermission(DatastoreDomain.DATA_STORE, Actions.write, scopeId)) };
if (!hasPermissions[AclConstants.BROKER_CONNECT_IDX]) {
throw new KapuaIllegalAccessException(permissionFactory.newPermission(DeviceLifecycleDomain.DEVICE_LIFECYCLE, Actions.connect, scopeId).toString());
}
loginCheckAccessTimeContext.stop();
// 3-4) build authMap
authMap = buildAuthMap(authDestinations, principal, hasPermissions, accountName, clientId, fullClientId);
// 4) find device
Context loginFindClientIdTimeContext = metricLoginFindClientIdTime.time();
deviceConnection = deviceConnectionService.findByClientId(scopeId, clientId);
loginFindClientIdTimeContext.stop();
Context loginFindDevTimeContext = metricLoginFindDevTime.time();
// send connect message
ConnectionId previousConnectionId = connectionMap.get(fullClientId);
boolean stealingLinkDetected = (previousConnectionId != null);
// Update map for stealing link detection on disconnect
connectionMap.put(fullClientId, info.getConnectionId());
if (deviceConnection == null) {
DeviceConnectionCreator deviceConnectionCreator = deviceConnectionFactory.newCreator(scopeId);
deviceConnectionCreator.setClientId(clientId);
deviceConnectionCreator.setClientIp(clientIp);
deviceConnectionCreator.setProtocol("MQTT");
// TODO to be filled with the proper value
deviceConnectionCreator.setServerIp(null);
deviceConnectionCreator.setUserId(userId);
deviceConnection = deviceConnectionService.create(deviceConnectionCreator);
} else {
deviceConnection.setClientIp(clientIp);
deviceConnection.setProtocol("MQTT");
// TODO to be filled with the proper value
deviceConnection.setServerIp(null);
deviceConnection.setUserId(userId);
deviceConnection.setStatus(DeviceConnectionStatus.CONNECTED);
deviceConnectionService.update(deviceConnection);
// TODO manage the stealing link event (may be a good idea to use different connect status (connect -stealing)?
if (stealingLinkDetected) {
metricLoginStealingLinkConnect.inc();
// stealing link detected, skip info
logger.warn("Detected Stealing link for cliend id {} - account - last connection id was {} - current connection id is {} - IP: {} - No connection status changes!", new Object[] { clientId, accountName, previousConnectionId, info.getConnectionId(), info.getClientIp() });
}
}
loginFindDevTimeContext.stop();
loginNormalUserTimeContext.stop();
Context loginSendLogingUpdateMsgTimeContex = metricLoginSendLoginUpdateMsgTime.time();
loginSendLogingUpdateMsgTimeContex.stop();
metricClientConnectedClient.inc();
}
logAuthDestinationToLog(authDestinations);
ConnectorDescriptor connectorDescriptor = connectorsDescriptorMap.get((((TransportConnector) context.getConnector()).getName()));
KapuaSecurityContext securityCtx = new KapuaSecurityContext(principal, authMap, (deviceConnection != null ? deviceConnection.getId() : null), connectionId, connectorDescriptor);
context.setSecurityContext(securityCtx);
// multiple account stealing link fix
info.setClientId(fullClientId);
context.setClientId(fullClientId);
} catch (Exception e) {
metricLoginFailure.inc();
// fix ENTMQ-731
if (e instanceof KapuaAuthenticationException) {
KapuaAuthenticationException kapuaException = (KapuaAuthenticationException) e;
KapuaErrorCode errorCode = kapuaException.getCode();
if (errorCode.equals(KapuaAuthenticationErrorCodes.INVALID_USERNAME) || errorCode.equals(KapuaAuthenticationErrorCodes.INVALID_CREDENTIALS) || errorCode.equals(KapuaAuthenticationErrorCodes.INVALID_CREDENTIALS_TOKEN_PROVIDED)) {
logger.warn("Invalid username or password for user {} ({})", username, e.getMessage());
// activeMQ will map CredentialException into a CONNECTION_REFUSED_BAD_USERNAME_OR_PASSWORD message (see javadoc on top of this method)
CredentialException ce = new CredentialException("Invalid username and/or password or disabled or expired account!");
ce.setStackTrace(e.getStackTrace());
metricLoginInvalidUserPassword.inc();
throw ce;
} else if (errorCode.equals(KapuaAuthenticationErrorCodes.LOCKED_USERNAME) || errorCode.equals(KapuaAuthenticationErrorCodes.DISABLED_USERNAME) || errorCode.equals(KapuaAuthenticationErrorCodes.EXPIRED_CREDENTIALS)) {
logger.warn("User {} not authorized ({})", username, e.getMessage());
// activeMQ-MQ will map SecurityException into a CONNECTION_REFUSED_NOT_AUTHORIZED message (see javadoc on top of this method)
SecurityException se = new SecurityException("User not authorized!");
se.setStackTrace(e.getStackTrace());
throw se;
}
}
// Excluded CredentialException, InvalidClientIDException, SecurityException all others exceptions will be mapped by activeMQ to a CONNECTION_REFUSED_SERVER_UNAVAILABLE message (see
// javadoc on top of this method)
// Not trapped exception now:
// KapuaException
logger.info("@@ error", e);
throw e;
} finally {
// 7) logout
Context loginShiroLogoutTimeContext = metricLoginShiroLogoutTime.time();
authenticationService.logout();
ThreadContext.unbindSubject();
loginShiroLogoutTimeContext.stop();
loginTotalContext.stop();
}
}
use of org.eclipse.kapua.KapuaIllegalAccessException in project kapua by eclipse.
the class DeviceExporterServlet method internalDoGet.
private void internalDoGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
try {
// parameter extraction
String format = request.getParameter("format");
String scopeIdString = request.getParameter("scopeIdString");
// data exporter
DeviceExporter deviceExporter = null;
if ("xls".equals(format)) {
deviceExporter = new DeviceExporterExcel(response);
} else if ("csv".equals(format)) {
deviceExporter = new DeviceExporterCsv(response);
} else {
throw new IllegalArgumentException("format");
}
if (scopeIdString == null || scopeIdString.isEmpty()) {
throw new IllegalArgumentException("account");
}
deviceExporter.init(scopeIdString);
//
// get the devices and append them to the exporter
KapuaLocator locator = KapuaLocator.getInstance();
DeviceRegistryService drs = locator.getService(DeviceRegistryService.class);
DeviceFactory drf = locator.getFactory(DeviceFactory.class);
int resultsCount = 0;
int offset = 0;
// paginate through the matching message
DeviceQuery dq = drf.newQuery(KapuaEid.parseShortId(scopeIdString));
dq.setLimit(250);
// Inserting filter parameter if specified
AndPredicate andPred = new AndPredicate();
String clientId = request.getParameter("clientId");
if (clientId != null && !clientId.isEmpty()) {
andPred = andPred.and(new AttributePredicate<String>(DevicePredicates.CLIENT_ID, clientId, Operator.STARTS_WITH));
}
String displayName = request.getParameter("displayName");
if (displayName != null && !displayName.isEmpty()) {
andPred = andPred.and(new AttributePredicate<String>(DevicePredicates.DISPLAY_NAME, displayName, Operator.STARTS_WITH));
}
String serialNumber = request.getParameter("serialNumber");
if (serialNumber != null && !serialNumber.isEmpty()) {
andPred = andPred.and(new AttributePredicate<String>(DevicePredicates.SERIAL_NUMBER, serialNumber));
}
String deviceStatus = request.getParameter("deviceStatus");
if (deviceStatus != null && !deviceStatus.isEmpty()) {
andPred = andPred.and(new AttributePredicate<DeviceStatus>(DevicePredicates.STATUS, DeviceStatus.valueOf(deviceStatus)));
}
String sortAttribute = request.getParameter("sortAttribute");
if (sortAttribute != null && !sortAttribute.isEmpty()) {
String sortOrderString = request.getParameter("sortOrder");
SortOrder sortOrder;
if (sortOrderString != null && !sortOrderString.isEmpty()) {
sortOrder = SortOrder.valueOf(sortOrderString);
} else {
sortOrder = SortOrder.ASCENDING;
}
if (sortAttribute.compareTo("CLIENT_ID") == 0) {
dq.setSortCriteria(new FieldSortCriteria(DevicePredicates.CLIENT_ID, sortOrder));
} else if (sortAttribute.compareTo("DISPLAY_NAME") == 0) {
dq.setSortCriteria(new FieldSortCriteria(DevicePredicates.DISPLAY_NAME, sortOrder));
} else if (sortAttribute.compareTo("LAST_EVENT_ON") == 0) {
dq.setSortCriteria(new FieldSortCriteria(DevicePredicates.LAST_EVENT_ON, sortOrder));
}
}
dq.setPredicate(andPred);
KapuaListResult<Device> results = null;
do {
dq.setOffset(offset);
results = drs.query(dq);
deviceExporter.append(results);
offset += results.getSize();
resultsCount += results.getSize();
} while (results.getSize() > 0);
// Close things up
deviceExporter.close();
} catch (IllegalArgumentException iae) {
response.sendError(400, "Illegal value for query parameter: " + iae.getMessage());
return;
} catch (KapuaEntityNotFoundException eenfe) {
response.sendError(400, eenfe.getMessage());
return;
} catch (KapuaUnauthenticatedException eiae) {
response.sendError(401, eiae.getMessage());
return;
} catch (KapuaIllegalAccessException eiae) {
response.sendError(403, eiae.getMessage());
return;
} catch (Exception e) {
s_logger.error("Error creating device export", e);
throw new ServletException(e);
}
}
use of org.eclipse.kapua.KapuaIllegalAccessException in project kapua by eclipse.
the class UploadRequest method doPostCommand.
private void doPostCommand(KapuaFormFields kapuaFormFields, HttpServletResponse resp) throws ServletException, IOException {
try {
List<FileItem> fileItems = kapuaFormFields.getFileItems();
final String scopeIdString = kapuaFormFields.get("scopeIdString");
final String deviceIdString = kapuaFormFields.get("deviceIdString");
final String command = kapuaFormFields.get("command");
final String password = kapuaFormFields.get("password");
final String timeoutString = kapuaFormFields.get("timeout");
if (scopeIdString == null || scopeIdString.isEmpty()) {
throw new IllegalArgumentException("scopeId");
}
if (deviceIdString == null || deviceIdString.isEmpty()) {
throw new IllegalArgumentException("deviceId");
}
if (command == null || command.isEmpty()) {
throw new IllegalArgumentException("command");
}
if (fileItems.size() > 1) {
throw new IllegalArgumentException("file");
}
Integer timeout = null;
if (timeoutString != null && !timeoutString.isEmpty()) {
try {
timeout = Integer.parseInt(timeoutString);
} catch (NumberFormatException nfe) {
throw new IllegalArgumentException("timeout");
}
}
KapuaLocator locator = KapuaLocator.getInstance();
DeviceCommandManagementService deviceService = locator.getService(DeviceCommandManagementService.class);
// FIXME: set a max size on the MQtt payload
byte[] data = fileItems.size() == 0 ? null : fileItems.get(0).get();
DeviceCommandFactory deviceCommandFactory = locator.getFactory(DeviceCommandFactory.class);
DeviceCommandInput commandInput = deviceCommandFactory.newCommandInput();
StringTokenizer st = new StringTokenizer(command);
int count = st.countTokens();
String cmd = count > 0 ? st.nextToken() : null;
String[] args = count > 1 ? new String[count - 1] : null;
int i = 0;
while (st.hasMoreTokens()) {
args[i++] = st.nextToken();
}
commandInput.setCommand(cmd);
commandInput.setPassword((password == null || password.isEmpty()) ? null : password);
commandInput.setArguments(args);
commandInput.setTimeout(timeout);
commandInput.setWorkingDir("/tmp/");
commandInput.setBody(data);
DeviceCommandOutput deviceCommandOutput = deviceService.exec(KapuaEid.parseShortId(scopeIdString), KapuaEid.parseShortId(deviceIdString), commandInput, null);
resp.setContentType("text/plain");
if (deviceCommandOutput.getStderr() != null && deviceCommandOutput.getStderr().length() > 0) {
resp.getWriter().println(deviceCommandOutput.getStderr());
}
if (deviceCommandOutput.getStdout() != null && deviceCommandOutput.getStdout().length() > 0) {
resp.getWriter().println(deviceCommandOutput.getStdout());
}
if (deviceCommandOutput.getExceptionMessage() != null && deviceCommandOutput.getExceptionMessage().length() > 0) {
resp.getWriter().println(deviceCommandOutput.getExceptionMessage());
}
} catch (IllegalArgumentException iae) {
resp.sendError(400, "Illegal value for query parameter: " + iae.getMessage());
return;
} catch (KapuaEntityNotFoundException eenfe) {
resp.sendError(400, eenfe.getMessage());
return;
} catch (KapuaUnauthenticatedException eiae) {
resp.sendError(401, eiae.getMessage());
return;
} catch (KapuaIllegalAccessException eiae) {
resp.sendError(403, eiae.getMessage());
return;
} catch (Exception e) {
s_logger.error("Error sending command", e);
throw new ServletException(e);
}
}
use of org.eclipse.kapua.KapuaIllegalAccessException in project kapua by eclipse.
the class UploadRequest method doPostConfigurationSnapshot.
private void doPostConfigurationSnapshot(KapuaFormFields kapuaFormFields, HttpServletResponse resp) throws ServletException, IOException {
try {
List<FileItem> fileItems = kapuaFormFields.getFileItems();
String scopeIdString = kapuaFormFields.get("scopeIdString");
String deviceIdString = kapuaFormFields.get("deviceIdString");
if (scopeIdString == null || scopeIdString.isEmpty()) {
throw new IllegalArgumentException("scopeIdString");
}
if (deviceIdString == null || deviceIdString.isEmpty()) {
throw new IllegalArgumentException("deviceIdString");
}
if (fileItems == null || fileItems.size() != 1) {
throw new IllegalArgumentException("configuration");
}
KapuaLocator locator = KapuaLocator.getInstance();
DeviceConfigurationManagementService deviceConfigurationManagementService = locator.getService(DeviceConfigurationManagementService.class);
FileItem fileItem = fileItems.get(0);
byte[] data = fileItem.get();
String xmlConfigurationString = new String(data, "UTF-8");
deviceConfigurationManagementService.put(KapuaEid.parseShortId(scopeIdString), KapuaEid.parseShortId(deviceIdString), xmlConfigurationString, null);
} catch (IllegalArgumentException iae) {
resp.sendError(400, "Illegal value for query parameter: " + iae.getMessage());
return;
} catch (KapuaEntityNotFoundException eenfe) {
resp.sendError(400, eenfe.getMessage());
return;
} catch (KapuaUnauthenticatedException eiae) {
resp.sendError(401, eiae.getMessage());
return;
} catch (KapuaIllegalAccessException eiae) {
resp.sendError(403, eiae.getMessage());
return;
} catch (Exception e) {
s_logger.error("Error posting configuration", e);
throw new ServletException(e);
}
}
use of org.eclipse.kapua.KapuaIllegalAccessException in project kapua by eclipse.
the class AccountServiceImpl method delete.
@Override
public void delete(KapuaId scopeId, KapuaId accountId) throws KapuaException {
//
// Validation of the fields
ArgumentValidator.notNull(accountId, "id");
ArgumentValidator.notNull(scopeId, "id.id");
//
// Check Access
Actions action = Actions.write;
KapuaLocator locator = KapuaLocator.getInstance();
AuthorizationService authorizationService = locator.getService(AuthorizationService.class);
PermissionFactory permissionFactory = locator.getFactory(PermissionFactory.class);
authorizationService.checkPermission(permissionFactory.newPermission(AccountDomain.ACCOUNT, action, scopeId));
// Check if it has children
if (this.findChildAccountsTrusted(accountId).size() > 0) {
throw new KapuaAccountException(KapuaAccountErrorCodes.OPERATION_NOT_ALLOWED, null, "This account cannot be deleted. Delete its child first.");
}
//
// Delete the Account
EntityManager em = AccountEntityManagerFactory.getInstance().createEntityManager();
try {
// Entity needs to be loaded in the context of the same EntityManger to be able to delete it afterwards
Account accountx = AccountDAO.find(em, accountId);
if (accountx == null) {
throw new KapuaEntityNotFoundException(Account.TYPE, accountId);
}
// do not allow deletion of the kapua admin account
SystemSetting settings = SystemSetting.getInstance();
if (settings.getString(SystemSettingKey.SYS_PROVISION_ACCOUNT_NAME).equals(accountx.getName())) {
throw new KapuaIllegalAccessException(action.name());
}
if (settings.getString(SystemSettingKey.SYS_ADMIN_ACCOUNT).equals(accountx.getName())) {
throw new KapuaIllegalAccessException(action.name());
}
em.beginTransaction();
AccountDAO.delete(em, accountId);
em.commit();
} catch (Exception e) {
em.rollback();
throw KapuaExceptionUtils.convertPersistenceException(e);
} finally {
em.close();
}
}
Aggregations