From 8403f243c0072ee2d4a1f1c144960ec4a68b9f41 Mon Sep 17 00:00:00 2001 From: Thisara-Welmilla Date: Tue, 3 Dec 2024 10:38:55 +0530 Subject: [PATCH 01/15] Add authentication DAO layer for user def auth mgt. --- .../pom.xml | 20 ++ .../common/cache/AuthenticatorCache.java | 47 +++ .../common/cache/AuthenticatorCacheEntry.java | 45 +++ .../common/cache/AuthenticatorCacheKey.java | 54 +++ .../dao/AuthenticatorManagementDAO.java | 91 +++++ .../impl/AuthenticatorManagementDAOImpl.java | 339 ++++++++++++++++++ .../impl/AuthenticatorManagementFacade.java | 107 ++++++ .../impl/CacheBackedAuthenticatorMgtDAO.java | 103 ++++++ 8 files changed, 806 insertions(+) create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCache.java create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCacheEntry.java create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCacheKey.java create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/AuthenticatorManagementDAO.java create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/CacheBackedAuthenticatorMgtDAO.java diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/pom.xml b/components/application-mgt/org.wso2.carbon.identity.application.common/pom.xml index 8fd520f4ec88..65d910a2d386 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/pom.xml +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/pom.xml @@ -61,6 +61,21 @@ org.wso2.carbon.identity.framework org.wso2.carbon.identity.central.log.mgt + + org.wso2.carbon.identity.framework + org.wso2.carbon.identity.testutil + test + + + org.mockito + mockito-core + test + + + com.h2database + h2 + test + org.wso2.carbon.identity.framework org.wso2.carbon.identity.action.management @@ -90,7 +105,11 @@ org.apache.axiom.*; version="${axiom.osgi.version.range}", org.apache.commons.logging; version="${import.package.version.commons.logging}", org.apache.commons.lang; version="${commons-lang.wso2.osgi.version.range}", + org.osgi.framework; version="${osgi.framework.imp.pkg.version.range}", + org.osgi.service.component; version="${osgi.service.component.imp.pkg.version.range}", org.apache.commons.collections; version="${commons-collections.wso2.osgi.version.range}", + org.wso2.carbon.database.utils.jdbc; version="${org.wso2.carbon.database.utils.version.range}", + org.wso2.carbon.database.utils.jdbc.exceptions; version="${org.wso2.carbon.database.utils.version.range}", org.apache.axis2.*; version="${axis2.osgi.version.range}", @@ -106,6 +125,7 @@ org.wso2.carbon.identity.core.util; version="${carbon.identity.package.import.version.range}", org.wso2.carbon.identity.core.cache; version="${carbon.identity.package.import.version.range}", org.wso2.carbon.identity.central.log.mgt.*; version="${carbon.identity.package.import.version.range}", + org.wso2.carbon.identity.action.management.*;version="${carbon.identity.package.import.version.range}", com.fasterxml.jackson.annotation; version="${com.fasterxml.jackson.annotation.version.range}" diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCache.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCache.java new file mode 100644 index 000000000000..b1495a2f30db --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCache.java @@ -0,0 +1,47 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.cache; + +import org.wso2.carbon.identity.core.cache.BaseCache; +import org.wso2.carbon.utils.CarbonUtils; + +/** + * Cache for the user defined local application authenticator configurations. + */ +public class AuthenticatorCache extends BaseCache { + + private static final String CACHE_NAME = "AuthenticatorCache"; + private static final AuthenticatorCache INSTANCE = new AuthenticatorCache(); + + private AuthenticatorCache() { + + super(CACHE_NAME); + } + + /** + * Get Authenticator cache by the name instance. + * + * @return Authenticator cache by name instance. + */ + public static AuthenticatorCache getInstance() { + + CarbonUtils.checkSecurity(); + return INSTANCE; + } +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCacheEntry.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCacheEntry.java new file mode 100644 index 000000000000..31b29923ecd0 --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCacheEntry.java @@ -0,0 +1,45 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.cache; + +import org.wso2.carbon.identity.application.common.model.UserDefinedLocalAuthenticatorConfig; +import org.wso2.carbon.identity.core.cache.CacheEntry; + +/** + * Cache Entry for the user defined local application authenticator configurations. + */ +public class AuthenticatorCacheEntry extends CacheEntry { + + private UserDefinedLocalAuthenticatorConfig authenticatorConfig; + + public AuthenticatorCacheEntry(UserDefinedLocalAuthenticatorConfig authenticatorConfig) { + + this.authenticatorConfig = authenticatorConfig; + } + + public UserDefinedLocalAuthenticatorConfig getAuthenticatorConfig() { + + return authenticatorConfig; + } + + public void setAuthenticatorConfig(UserDefinedLocalAuthenticatorConfig authenticatorConfig) { + + this.authenticatorConfig = authenticatorConfig; + } +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCacheKey.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCacheKey.java new file mode 100644 index 000000000000..849aade9b671 --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCacheKey.java @@ -0,0 +1,54 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.cache; + +import org.wso2.carbon.identity.core.cache.CacheKey; + +/** + * Cache key for the user defined local application authenticator configurations. + */ +public class AuthenticatorCacheKey extends CacheKey { + + private final String authenticatorName; + + public AuthenticatorCacheKey(String authenticatorName) { + + this.authenticatorName = authenticatorName; + } + + public String getAuthenticatorName() { + + return authenticatorName; + } + + @Override + public boolean equals(Object o) { + + if (!(o instanceof AuthenticatorCacheKey)) { + return false; + } + return authenticatorName.equals(((AuthenticatorCacheKey) o).getAuthenticatorName()); + } + + @Override + public int hashCode() { + + return authenticatorName.hashCode(); + } +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/AuthenticatorManagementDAO.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/AuthenticatorManagementDAO.java new file mode 100644 index 000000000000..32b406995cd6 --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/AuthenticatorManagementDAO.java @@ -0,0 +1,91 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.dao; + +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtException; +import org.wso2.carbon.identity.application.common.model.UserDefinedLocalAuthenticatorConfig; + +import java.util.List; + +/** + * This interface performs CRUD operations for the user defined local application authenticator configurations. + */ +public interface AuthenticatorManagementDAO { + + /** + * Create a new user defined local application authenticator configuration. + * + * @param authenticatorConfig Local application authenticator configuration. + * @param tenantId Tenant Id. + * + * @return Created UserDefinedLocalAuthenticatorConfig. + * @throws AuthenticatorMgtException If an error occurs while adding the authenticator configuration. + */ + UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( + UserDefinedLocalAuthenticatorConfig authenticatorConfig, int tenantId) throws AuthenticatorMgtException; + + /** + * Update a user defined local application authenticator configuration. + * + * @param existingAuthenticatorConfig Existing Local application authenticator configuration. + * @param updatedAuthenticatorConfig New local application authenticator configuration. + * @param tenantId Tenant Id. + * + * @return Updated UserDefinedLocalAuthenticatorConfig. + * @throws AuthenticatorMgtException If an error occurs while updating the authenticator configuration. + */ + UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator( + UserDefinedLocalAuthenticatorConfig existingAuthenticatorConfig, + UserDefinedLocalAuthenticatorConfig updatedAuthenticatorConfig, int tenantId) + throws AuthenticatorMgtException; + + /** + * Retrieve a Local user defined Application Authenticator configuration by name. + * + * @param authenticatorConfigName Name of the local application authenticator configuration. + * @param tenantId Tenant Id. + * + * @return Retrieved UserDefinedLocalAuthenticatorConfig + * @throws AuthenticatorMgtException If an error occurs while retrieving the authenticator configuration. + */ + UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator( + String authenticatorConfigName, int tenantId) throws AuthenticatorMgtException; + + /** + * Retrieve all user defined local application authenticator configurations. + * + * @param tenantId Tenant Id. + * + * @return Retrieved UserDefinedLocalAuthenticatorConfig + * @throws AuthenticatorMgtException If an error occurs while retrieving the authenticator configurations. + */ + List getAllUserDefinedLocalAuthenticators(int tenantId) + throws AuthenticatorMgtException; + + /** + * Create a new user defined local application authenticator configuration. + * + * @param authenticatorConfigName Name of the local application authenticator configuration. + * @param tenantId Tenant Id. + * + * @throws AuthenticatorMgtException If an error occurs while deleting the authenticator configuration. + */ + void deleteUserDefinedLocalAuthenticator(String authenticatorConfigName, UserDefinedLocalAuthenticatorConfig + authenticatorConfig, int tenantId) throws AuthenticatorMgtException; +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java new file mode 100644 index 000000000000..89f75b53fcd5 --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java @@ -0,0 +1,339 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.dao.impl; + +import org.apache.commons.logging.Log; +import org.apache.commons.logging.LogFactory; +import org.wso2.carbon.database.utils.jdbc.NamedPreparedStatement; +import org.wso2.carbon.identity.application.common.constant.AuthenticatorMgtSQLConstants.Column; +import org.wso2.carbon.identity.application.common.constant.AuthenticatorMgtSQLConstants.Query; +import org.wso2.carbon.identity.application.common.dao.AuthenticatorManagementDAO; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtException; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtServerException; +import org.wso2.carbon.identity.application.common.model.Property; +import org.wso2.carbon.identity.application.common.model.UserDefinedLocalAuthenticatorConfig; +import org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.AuthenticatorMgtError; +import org.wso2.carbon.identity.base.AuthenticatorPropertyConstants.AuthenticationType; +import org.wso2.carbon.identity.base.AuthenticatorPropertyConstants.DefinedByType; +import org.wso2.carbon.identity.core.util.IdentityDatabaseUtil; +import org.wso2.carbon.identity.core.util.IdentityTenantUtil; + +import java.sql.Connection; +import java.sql.ResultSet; +import java.sql.SQLException; +import java.util.ArrayList; +import java.util.List; + +import static org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.buildServerException; + +/** + * This class implements the AuthenticatorManagementDAO interface which perform CRUD operation on database. + */ +public class AuthenticatorManagementDAOImpl implements AuthenticatorManagementDAO { + + private static final Log LOG = LogFactory.getLog(AuthenticatorManagementDAOImpl.class); + public static final String IS_TRUE_VALUE = "1"; + public static final String IS_FALSE_VALUE = "0"; + public static final String LOCAL_IDP_NAME = "LOCAL"; + + @Override + public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( + UserDefinedLocalAuthenticatorConfig authenticatorConfig, int tenantId) throws AuthenticatorMgtException { + + Connection dbConnection = IdentityDatabaseUtil.getDBConnection(true); + + try (NamedPreparedStatement statement = new NamedPreparedStatement(dbConnection, Query.ADD_AUTHENTICATOR_SQL)) { + statement.setString(Column.NAME, authenticatorConfig.getName()); + statement.setString(Column.DISPLAY_NAME, authenticatorConfig.getDisplayName()); + statement.setString(Column.DEFINED_BY, authenticatorConfig.getDefinedByType().toString()); + statement.setString(Column.AUTHENTICATION_TYPE, authenticatorConfig.getAuthenticationType().toString()); + statement.setInt(Column.IS_ENABLED, authenticatorConfig.isEnabled() ? 1 : 0); + statement.setString(Column.IDP_NAME, LOCAL_IDP_NAME); + statement.setInt(Column.TENANT_ID, tenantId); + statement.executeUpdate(); + + if (authenticatorConfig.getProperties() != null) { + + int authenticatorConfigID = getAuthenticatorIdentifier(dbConnection, authenticatorConfig.getName(), + tenantId); + addAuthenticatorProperties(dbConnection, authenticatorConfigID, authenticatorConfig.getProperties(), + tenantId); + } + IdentityDatabaseUtil.commitTransaction(dbConnection); + + return getUserDefinedLocalAuthenticatorByName(dbConnection, authenticatorConfig.getName(), tenantId); + } catch (SQLException e) { + if (LOG.isDebugEnabled()) { + LOG.debug(String.format("Error while adding the authenticator: %s in tenant domain: %s. " + + "Rolling back added Authenticator information.", authenticatorConfig.getName(), + IdentityTenantUtil.getTenantDomain(tenantId))); + } + IdentityDatabaseUtil.rollbackTransaction(dbConnection); + throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_ADDING_AUTHENTICATOR, e); + } finally { + IdentityDatabaseUtil.closeConnection(dbConnection); + } + } + + @Override + public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator( + UserDefinedLocalAuthenticatorConfig existingAuthenticatorConfig, + UserDefinedLocalAuthenticatorConfig updatedAuthenticatorConfig, int tenantId) + throws AuthenticatorMgtException { + + Connection dbConnection = IdentityDatabaseUtil.getDBConnection(true); + try { + if (isBasicInfoUpdated(existingAuthenticatorConfig, updatedAuthenticatorConfig)) { + try (NamedPreparedStatement statement = new NamedPreparedStatement(dbConnection, + Query.UPDATE_AUTHENTICATOR_SQL)) { + statement.setString(Column.DISPLAY_NAME, updatedAuthenticatorConfig.getDisplayName()); + statement.setInt(Column.IS_ENABLED, updatedAuthenticatorConfig.isEnabled() ? 1 : 0); + statement.setString(Column.NAME, existingAuthenticatorConfig.getName()); + statement.setInt(Column.TENANT_ID, tenantId); + statement.executeUpdate(); + } + } + + // Will delete all the properties of given authenticator and add the updated properties. + int authenticatorConfigID = getAuthenticatorIdentifier(dbConnection, + existingAuthenticatorConfig.getName(), tenantId); + deletedAuthenticatorProperties(dbConnection, authenticatorConfigID, tenantId); + addAuthenticatorProperties(dbConnection, authenticatorConfigID, updatedAuthenticatorConfig.getProperties(), + tenantId); + + IdentityDatabaseUtil.commitTransaction(dbConnection); + + return getUserDefinedLocalAuthenticatorByName(dbConnection, updatedAuthenticatorConfig.getName(), tenantId); + } catch (SQLException e) { + if (LOG.isDebugEnabled()) { + LOG.debug(String.format("Error while updating the authenticator: %s in tenant domain: %s. " + + "Rolling back updated Authenticator information.", + existingAuthenticatorConfig.getName(), IdentityTenantUtil.getTenantDomain(tenantId))); + } + IdentityDatabaseUtil.rollbackTransaction(dbConnection); + throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_UPDATING_AUTHENTICATOR, e); + } finally { + IdentityDatabaseUtil.closeConnection(dbConnection); + } + } + + @Override + public UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator( + String authenticatorConfigName, int tenantId) throws AuthenticatorMgtException { + + Connection dbConnection = IdentityDatabaseUtil.getDBConnection(false); + try { + return getUserDefinedLocalAuthenticatorByName(dbConnection, authenticatorConfigName, tenantId); + } finally { + IdentityDatabaseUtil.closeConnection(dbConnection); + } + } + + @Override + public List getAllUserDefinedLocalAuthenticators(int tenantId) + throws AuthenticatorMgtException { + + try (Connection dbConnection = IdentityDatabaseUtil.getDBConnection(true); + NamedPreparedStatement statement = new NamedPreparedStatement(dbConnection, + Query.GET_ALL_USER_DEFINED_AUTHENTICATOR_SQL)) { + statement.setString(Column.DEFINED_BY, DefinedByType.USER.toString()); + statement.setInt(Column.TENANT_ID, tenantId); + + List allUserDefinedLocalConfigs = new ArrayList<>(); + try (ResultSet rs = statement.executeQuery()) { + while (rs.next()) { + UserDefinedLocalAuthenticatorConfig config = getLocalAuthenticatorConfigBasedOnType( + rs.getString(Column.AUTHENTICATION_TYPE)); + config.setName(rs.getString(Column.NAME)); + config.setDisplayName(rs.getString(Column.DISPLAY_NAME)); + config.setEnabled(rs.getString(Column.IS_ENABLED).equals(IS_TRUE_VALUE)); + config.setDefinedByType(DefinedByType.valueOf(rs.getString(Column.DEFINED_BY))); + + int authenticatorConfigID = getAuthenticatorIdentifier(dbConnection, config.getName(), tenantId); + try (NamedPreparedStatement statementProp = new NamedPreparedStatement(dbConnection, + Query.GET_AUTHENTICATOR_PROP_SQL)) { + statementProp.setInt(Column.AUTHENTICATOR_ID, authenticatorConfigID); + statementProp.setInt(Column.TENANT_ID, tenantId); + + try (ResultSet rsProp = statementProp.executeQuery()) { + List properties = new ArrayList<>(); + while (rsProp.next()) { + Property property = new Property(); + property.setName(rsProp.getString(Column.PROPERTY_KEY)); + property.setValue(rsProp.getString(Column.PROPERTY_VALUE)); + property.setConfidential(false); + properties.add(property); + } + config.setProperties(properties.toArray(new Property[0])); + } + } + + allUserDefinedLocalConfigs.add(config); + } + } + + return allUserDefinedLocalConfigs; + } catch (SQLException e) { + if (LOG.isDebugEnabled()) { + LOG.debug(String.format("Error while retrieving the all user defined local authenticators in tenant " + + "domain: %s.", IdentityTenantUtil.getTenantDomain(tenantId))); + } + throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_DELETING_AUTHENTICATOR, e); + } + } + + @Override + public void deleteUserDefinedLocalAuthenticator(String authenticatorConfigName, + UserDefinedLocalAuthenticatorConfig authenticatorConfig, int tenantId) throws AuthenticatorMgtException { + + Connection dbConnection = IdentityDatabaseUtil.getDBConnection(true); + try (NamedPreparedStatement statement = new NamedPreparedStatement(dbConnection, + Query.DELETE_AUTHENTICATOR_SQL)) { + statement.setString(Column.NAME, authenticatorConfigName); + statement.setInt(Column.TENANT_ID, tenantId); + statement.executeUpdate(); + + IdentityDatabaseUtil.commitTransaction(dbConnection); + } catch (SQLException e) { + if (LOG.isDebugEnabled()) { + LOG.debug(String.format("Error while deleting the authenticator: %s in tenant domain: %s. " + + "Rolling back deleted Authenticator information.", authenticatorConfigName, + IdentityTenantUtil.getTenantDomain(tenantId))); + } + IdentityDatabaseUtil.rollbackTransaction(dbConnection); + throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_DELETING_AUTHENTICATOR, e); + } finally { + IdentityDatabaseUtil.closeConnection(dbConnection); + } + } + + private UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticatorByName( + Connection dbConnection, String authenticatorConfigName, int tenantId) + throws AuthenticatorMgtServerException { + + UserDefinedLocalAuthenticatorConfig config = null; + try (NamedPreparedStatement statement = new NamedPreparedStatement(dbConnection, Query.GET_AUTHENTICATOR_SQL)) { + statement.setString(Column.NAME, authenticatorConfigName); + statement.setInt(Column.TENANT_ID, tenantId); + statement.setString(Column.DEFINED_BY, DefinedByType.USER.toString()); + + try (ResultSet rs = statement.executeQuery()) { + if (rs.next()) { + config = getLocalAuthenticatorConfigBasedOnType(rs.getString(Column.AUTHENTICATION_TYPE)); + config.setName(rs.getString(Column.NAME)); + config.setDisplayName(rs.getString(Column.DISPLAY_NAME)); + config.setEnabled(rs.getString(Column.IS_ENABLED).equals(IS_TRUE_VALUE)); + config.setDefinedByType(DefinedByType.USER); + } + } + + if (config == null) { + return null; + } + + int authenticatorConfigID = getAuthenticatorIdentifier(dbConnection, config.getName(), tenantId); + try (NamedPreparedStatement statementProp = new NamedPreparedStatement(dbConnection, + Query.GET_AUTHENTICATOR_PROP_SQL)) { + statementProp.setInt(Column.AUTHENTICATOR_ID, authenticatorConfigID); + statementProp.setInt(Column.TENANT_ID, tenantId); + + try (ResultSet rs = statementProp.executeQuery()) { + List properties = new ArrayList<>(); + while (rs.next()) { + Property property = new Property(); + property.setName(rs.getString(Column.PROPERTY_KEY)); + property.setValue(rs.getString(Column.PROPERTY_VALUE)); + property.setConfidential(false); + properties.add(property); + } + config.setProperties(properties.toArray(new Property[0])); + } + } + + IdentityDatabaseUtil.commitTransaction(dbConnection); + return config; + } catch (SQLException e) { + throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_RETRIEVING_AUTHENTICATOR_BY_NAME, e); + } + } + + private UserDefinedLocalAuthenticatorConfig getLocalAuthenticatorConfigBasedOnType(String authenticationType) { + + if (AuthenticationType.VERIFICATION.toString().equals(authenticationType)) { + return new UserDefinedLocalAuthenticatorConfig(AuthenticationType.VERIFICATION); + } + return new UserDefinedLocalAuthenticatorConfig(AuthenticationType.IDENTIFICATION); + } + + private boolean isBasicInfoUpdated(UserDefinedLocalAuthenticatorConfig existingAuthenticatorConfig, + UserDefinedLocalAuthenticatorConfig updatedAuthenticatorConfig) { + + return !existingAuthenticatorConfig.getDisplayName().equals(updatedAuthenticatorConfig.getDisplayName()) || + existingAuthenticatorConfig.isEnabled() != updatedAuthenticatorConfig.isEnabled(); + } + + private int getAuthenticatorIdentifier(Connection dbConnection, String authenticatorConfigName, + int tenantId) throws AuthenticatorMgtServerException, SQLException { + + try (NamedPreparedStatement statement = new NamedPreparedStatement(dbConnection, + Query.GET_AUTHENTICATOR_ID_SQL)) { + statement.setString(Column.NAME, authenticatorConfigName); + statement.setInt(Column.TENANT_ID, tenantId); + + try (ResultSet rs = statement.executeQuery()) { + if (rs.next()) { + return rs.getInt(Column.ID); + } + } + IdentityDatabaseUtil.commitTransaction(dbConnection); + } + throw buildServerException(AuthenticatorMgtError.ERROR_CODE_NO_AUTHENTICATOR_FOUND, authenticatorConfigName); + } + + private void deletedAuthenticatorProperties(Connection dbConnection, int authenticatorConfigID, int tenantId) + throws SQLException { + + try (NamedPreparedStatement statementDeleteProp = new NamedPreparedStatement(dbConnection, + Query.DELETE_AUTHENTICATOR_PROP_SQL)) { + statementDeleteProp.setInt(Column.AUTHENTICATOR_ID, authenticatorConfigID); + statementDeleteProp.setInt(Column.TENANT_ID, tenantId); + statementDeleteProp.executeUpdate(); + } + } + + private void addAuthenticatorProperties(Connection dbConnection, int authenticatorConfigID, Property[] properties, + int tenantId) throws SQLException { + + try (NamedPreparedStatement statementProp = new NamedPreparedStatement(dbConnection, + Query.ADD_AUTHENTICATOR_PROP_SQL)) { + for (Property prop : properties) { + statementProp.setInt(Column.AUTHENTICATOR_ID, authenticatorConfigID); + statementProp.setInt(Column.TENANT_ID, tenantId); + statementProp.setString(Column.PROPERTY_KEY, prop.getName()); + statementProp.setString(Column.PROPERTY_VALUE, prop.getValue()); + if (prop.isConfidential()) { + statementProp.setString(Column.IS_SECRET, IS_TRUE_VALUE); + } else { + statementProp.setString(Column.IS_SECRET, IS_FALSE_VALUE); + } + statementProp.executeUpdate(); + } + } + } +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java new file mode 100644 index 000000000000..2e086b8eafb6 --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java @@ -0,0 +1,107 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.dao.impl; + +import org.wso2.carbon.identity.application.common.dao.AuthenticatorManagementDAO; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtException; +import org.wso2.carbon.identity.application.common.model.UserDefinedLocalAuthenticatorConfig; +import org.wso2.carbon.identity.application.common.util.UserDefinedAuthenticatorEndpointConfigManager; + +import java.util.List; + +/** + * This class responsible for managing authenticator endpoint configurations for the user defined local + * authenticators. + */ +public class AuthenticatorManagementFacade implements AuthenticatorManagementDAO { + + private final AuthenticatorManagementDAO dao; + private UserDefinedAuthenticatorEndpointConfigManager endpointConfigManager = + new UserDefinedAuthenticatorEndpointConfigManager(); + + public AuthenticatorManagementFacade(AuthenticatorManagementDAO dao) { + + this.dao = dao; + } + + @Override + public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( + UserDefinedLocalAuthenticatorConfig authenticatorConfig, int tenantId) throws AuthenticatorMgtException { + + endpointConfigManager.addEndpointConfigurations(authenticatorConfig, tenantId); + try { + return endpointConfigManager.resolveEndpointConfigurations( + dao.addUserDefinedLocalAuthenticator(authenticatorConfig, tenantId), tenantId); + } catch (AuthenticatorMgtException e) { + endpointConfigManager.deleteEndpointConfigurations(authenticatorConfig, tenantId); + throw e; + } + } + + @Override + public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticatorConfig + existingAuthenticatorConfig, UserDefinedLocalAuthenticatorConfig newAuthenticatorConfig, + int tenantId) throws AuthenticatorMgtException { + + endpointConfigManager.updateEndpointConfigurations(newAuthenticatorConfig, existingAuthenticatorConfig, + tenantId); + try { + return endpointConfigManager.resolveEndpointConfigurations( + dao.updateUserDefinedLocalAuthenticator(existingAuthenticatorConfig, newAuthenticatorConfig, + tenantId), tenantId); + } catch (AuthenticatorMgtException e) { + endpointConfigManager.updateEndpointConfigurations(existingAuthenticatorConfig, newAuthenticatorConfig, + tenantId); + throw e; + } + } + + @Override + public UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator( + String authenticatorConfigName, int tenantId) throws AuthenticatorMgtException { + + UserDefinedLocalAuthenticatorConfig config = dao.getUserDefinedLocalAuthenticator(authenticatorConfigName, + tenantId); + return endpointConfigManager.resolveEndpointConfigurations(config, tenantId); + } + + @Override + public List getAllUserDefinedLocalAuthenticators(int tenantId) + throws AuthenticatorMgtException { + + List configList = dao.getAllUserDefinedLocalAuthenticators(tenantId); + for (UserDefinedLocalAuthenticatorConfig config : configList) { + endpointConfigManager.resolveEndpointConfigurations(config, tenantId); + } + return configList; + } + + @Override + public void deleteUserDefinedLocalAuthenticator(String authenticatorConfigName, UserDefinedLocalAuthenticatorConfig + authenticatorConfig, int tenantId) throws AuthenticatorMgtException { + + endpointConfigManager.deleteEndpointConfigurations(authenticatorConfig, tenantId); + try { + dao.deleteUserDefinedLocalAuthenticator(authenticatorConfigName, authenticatorConfig, tenantId); + } catch (AuthenticatorMgtException e) { + endpointConfigManager.addEndpointConfigurations(authenticatorConfig, tenantId); + throw e; + } + } +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/CacheBackedAuthenticatorMgtDAO.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/CacheBackedAuthenticatorMgtDAO.java new file mode 100644 index 000000000000..d5e683b5752d --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/CacheBackedAuthenticatorMgtDAO.java @@ -0,0 +1,103 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.dao.impl; + +import org.apache.commons.logging.Log; +import org.apache.commons.logging.LogFactory; +import org.wso2.carbon.identity.application.common.cache.AuthenticatorCache; +import org.wso2.carbon.identity.application.common.cache.AuthenticatorCacheEntry; +import org.wso2.carbon.identity.application.common.cache.AuthenticatorCacheKey; +import org.wso2.carbon.identity.application.common.dao.AuthenticatorManagementDAO; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtException; +import org.wso2.carbon.identity.application.common.model.UserDefinedLocalAuthenticatorConfig; + +import java.util.List; + +/** + * This class implements the Cache backed AuthenticatorManagementDAO interface. + */ +public class CacheBackedAuthenticatorMgtDAO implements AuthenticatorManagementDAO { + + private static final Log LOG = LogFactory.getLog(CacheBackedAuthenticatorMgtDAO.class); + private final AuthenticatorCache authenticatorCache; + private final AuthenticatorManagementFacade authenticatorMgtFacade; + + public CacheBackedAuthenticatorMgtDAO(AuthenticatorManagementDAO authenticatorManagementDAO) { + + authenticatorMgtFacade = new AuthenticatorManagementFacade(authenticatorManagementDAO); + authenticatorCache = AuthenticatorCache.getInstance(); + } + + @Override + public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( + UserDefinedLocalAuthenticatorConfig authenticatorConfig, int tenantId) throws AuthenticatorMgtException { + + UserDefinedLocalAuthenticatorConfig createdConfig = authenticatorMgtFacade.addUserDefinedLocalAuthenticator( + authenticatorConfig, tenantId); + + AuthenticatorCacheKey cacheKey = new AuthenticatorCacheKey(authenticatorConfig.getName()); + authenticatorCache.addToCache(cacheKey, new AuthenticatorCacheEntry(createdConfig), tenantId); + return createdConfig; + } + + @Override + public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticatorConfig + existingAuthenticatorConfig, UserDefinedLocalAuthenticatorConfig newAuthenticatorConfig, + int tenantId) throws AuthenticatorMgtException { + + AuthenticatorCacheKey cacheKey = new AuthenticatorCacheKey(existingAuthenticatorConfig.getName()); + authenticatorCache.clearCacheEntry(cacheKey, tenantId); + + return authenticatorMgtFacade.updateUserDefinedLocalAuthenticator( + existingAuthenticatorConfig, newAuthenticatorConfig, tenantId); + } + + @Override + public UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator( + String authenticatorConfigName, int tenantId) throws AuthenticatorMgtException { + + AuthenticatorCacheKey cacheKey = new AuthenticatorCacheKey(authenticatorConfigName); + AuthenticatorCacheEntry entry = authenticatorCache.getValueFromCache(cacheKey, tenantId); + + if (entry != null) { + return entry.getAuthenticatorConfig(); + } + + UserDefinedLocalAuthenticatorConfig authenticatorConfig = authenticatorMgtFacade + .getUserDefinedLocalAuthenticator(authenticatorConfigName, tenantId); + authenticatorCache.addToCache(cacheKey, new AuthenticatorCacheEntry(authenticatorConfig), tenantId); + return authenticatorConfig; + } + + @Override + public List getAllUserDefinedLocalAuthenticators(int tenantId) + throws AuthenticatorMgtException { + + return authenticatorMgtFacade.getAllUserDefinedLocalAuthenticators(tenantId); + } + + @Override + public void deleteUserDefinedLocalAuthenticator(String authenticatorConfigName, + UserDefinedLocalAuthenticatorConfig authenticatorConfig, int tenantId) throws AuthenticatorMgtException { + + authenticatorCache.clearCacheEntry(new AuthenticatorCacheKey(authenticatorConfigName), tenantId); + authenticatorMgtFacade.deleteUserDefinedLocalAuthenticator(authenticatorConfigName, authenticatorConfig, + tenantId); + } +} From a22f2fff7706a20c12f02ed558ae4da65ba04e85 Mon Sep 17 00:00:00 2001 From: Thisara-Welmilla Date: Tue, 3 Dec 2024 22:47:11 +0530 Subject: [PATCH 02/15] Add authentication service layer for user def auth mgt. --- .../ApplicationAuthenticatorService.java | 157 ++++++++++++++ .../AuthenticatorMgtSQLConstants.java | 86 ++++++++ .../AuthenticatorMgtClientException.java | 30 +++ .../exception/AuthenticatorMgtException.java | 63 ++++++ .../AuthenticatorMgtServerException.java | 36 ++++ ...uthenticatorMgtServerRuntimeException.java | 53 +++++ .../ApplicationCommonServiceComponent.java | 67 ++++++ .../ApplicationCommonServiceDataHolder.java | 65 ++++++ ...erDefinedFederatedAuthenticatorConfig.java | 6 +- .../UserDefinedLocalAuthenticatorConfig.java | 28 ++- .../AuthenticatorMgtExceptionBuilder.java | 144 +++++++++++++ ...nedAuthenticatorEndpointConfigManager.java | 191 ++++++++++++++++++ ...serDefinedLocalAuthenticatorValidator.java | 80 ++++++++ 13 files changed, 1000 insertions(+), 6 deletions(-) create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/constant/AuthenticatorMgtSQLConstants.java create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtClientException.java create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtException.java create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtServerException.java create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtServerRuntimeException.java create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/internal/ApplicationCommonServiceComponent.java create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/internal/ApplicationCommonServiceDataHolder.java create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/AuthenticatorMgtExceptionBuilder.java create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedAuthenticatorEndpointConfigManager.java create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedLocalAuthenticatorValidator.java diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java index e93a82f42b75..f1ec5c5aa264 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java @@ -18,23 +18,41 @@ package org.wso2.carbon.identity.application.common; +import org.apache.commons.logging.Log; +import org.apache.commons.logging.LogFactory; +import org.wso2.carbon.identity.application.common.dao.impl.AuthenticatorManagementDAOImpl; +import org.wso2.carbon.identity.application.common.dao.impl.CacheBackedAuthenticatorMgtDAO; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtException; import org.wso2.carbon.identity.application.common.model.FederatedAuthenticatorConfig; import org.wso2.carbon.identity.application.common.model.LocalAuthenticatorConfig; import org.wso2.carbon.identity.application.common.model.RequestPathAuthenticatorConfig; +import org.wso2.carbon.identity.application.common.model.UserDefinedLocalAuthenticatorConfig; +import org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.AuthenticatorMgtError; +import org.wso2.carbon.identity.application.common.util.UserDefinedLocalAuthenticatorValidator; +import org.wso2.carbon.identity.base.AuthenticatorPropertyConstants.DefinedByType; +import org.wso2.carbon.identity.core.util.IdentityTenantUtil; import java.util.ArrayList; import java.util.List; +import static org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.buildClientException; +import static org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.buildRuntimeServerException; + /** * Application authenticator service. */ public class ApplicationAuthenticatorService { private static volatile ApplicationAuthenticatorService instance; + private static final Log LOG = LogFactory.getLog(ApplicationAuthenticatorService.class); + private static final CacheBackedAuthenticatorMgtDAO CACHE_BACKED_DAO = + new CacheBackedAuthenticatorMgtDAO(new AuthenticatorManagementDAOImpl()); private List localAuthenticators = new ArrayList<>(); private List federatedAuthenticators = new ArrayList<>(); private List requestPathAuthenticators = new ArrayList<>(); + private UserDefinedLocalAuthenticatorValidator authenticatorValidator = + new UserDefinedLocalAuthenticatorValidator(); public static ApplicationAuthenticatorService getInstance() { if (instance == null) { @@ -51,6 +69,17 @@ public List getLocalAuthenticators() { return this.localAuthenticators; } + /** + * This returns user defined local authenticators. + * + * @return Retrieved LocalAuthenticatorConfig. + */ + public List getAllUserDefinedLocalAuthenticators(String tenantDomain) + throws AuthenticatorMgtException { + + return CACHE_BACKED_DAO.getAllUserDefinedLocalAuthenticators(IdentityTenantUtil.getTenantId(tenantDomain)); + } + public List getFederatedAuthenticators() { return this.federatedAuthenticators; } @@ -59,6 +88,16 @@ public List getRequestPathAuthenticators() { return this.requestPathAuthenticators; } + /** + * This returns only SYSTEM defined local authenticator by name. + * + * @param name The name of the Local Application Authenticator configuration. + * @return Retrieved LocalAuthenticatorConfig. + * + * @deprecated It is recommended to use {@link #getLocalAuthenticatorByName(String, String)}, + * which supports retrieving both USER and SYSTEM defined Local Application Authenticator configuration by name. + */ + @Deprecated public LocalAuthenticatorConfig getLocalAuthenticatorByName(String name) { for (LocalAuthenticatorConfig localAuthenticator : localAuthenticators) { if (localAuthenticator.getName().equals(name)) { @@ -68,6 +107,27 @@ public LocalAuthenticatorConfig getLocalAuthenticatorByName(String name) { return null; } + /** + * Retrieve both USER and SYSTEM defined Local Application Authenticator configuration by name. + * + * @param name The name of the Local Application Authenticator configuration. + * @param tenantDomain Tenant domain. + * @return Retrieved LocalAuthenticatorConfig. + * @throws AuthenticatorMgtException If an error occurs while retrieving the authenticator configuration by name. + */ + public LocalAuthenticatorConfig getLocalAuthenticatorByName(String name, String tenantDomain) + throws AuthenticatorMgtException { + + /* First, check whether an authenticator by the given name is in the system defined authenticators list. + If not, check in user defined authenticators. */ + for (LocalAuthenticatorConfig localAuthenticator : localAuthenticators) { + if (localAuthenticator.getName().equals(name)) { + return localAuthenticator; + } + } + return getUserDefinedLocalAuthenticator(name, tenantDomain); + } + public FederatedAuthenticatorConfig getFederatedAuthenticatorByName(String name) { for (FederatedAuthenticatorConfig federatedAuthenticator : federatedAuthenticators) { if (federatedAuthenticator.getName().equals(name)) { @@ -87,7 +147,12 @@ public RequestPathAuthenticatorConfig getRequestPathAuthenticatorByName(String n } public void addLocalAuthenticator(LocalAuthenticatorConfig authenticator) { + if (authenticator != null) { + if (authenticator.getDefinedByType() != DefinedByType.SYSTEM) { + throw buildRuntimeServerException( + AuthenticatorMgtError.ERROR_CODE_INVALID_DEFINED_BY_AUTH_PROVIDED, null); + } localAuthenticators.add(authenticator); } } @@ -121,4 +186,96 @@ public void removeRequestPathAuthenticator(RequestPathAuthenticatorConfig authen requestPathAuthenticators.remove(authenticator); } } + + /** + * Create a user defined Local Application Authenticator configuration. + * + * @param authenticatorConfig The Local Application Authenticator configuration. + * @param tenantDomain Tenant domain. + * @return Updated LocalAuthenticatorConfig. + * @throws AuthenticatorMgtException If an error occurs while creating the authenticator configuration. + */ + public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( + UserDefinedLocalAuthenticatorConfig authenticatorConfig, String tenantDomain) + throws AuthenticatorMgtException { + + LocalAuthenticatorConfig config = getLocalAuthenticatorByName(authenticatorConfig.getName(), tenantDomain); + if (config != null) { + throw buildClientException(AuthenticatorMgtError.ERROR_AUTHENTICATOR_ALREADY_EXIST, + authenticatorConfig.getName()); + } + authenticatorValidator.validateAuthenticatorName(authenticatorConfig.getName()); + authenticatorValidator.validateForBlank("Display name", authenticatorConfig.getDisplayName()); + authenticatorValidator.validateDefinedByType(authenticatorConfig.getDefinedByType()); + + return CACHE_BACKED_DAO.addUserDefinedLocalAuthenticator( + authenticatorConfig, IdentityTenantUtil.getTenantId(tenantDomain)); + } + + /** + * Update a user defined Local Application Authenticator configuration. + * + * @param authenticatorConfig The Local Application Authenticator configuration. + * @param tenantDomain Tenant Domain. + * @return Updated UserDefinedLocalAuthenticatorConfig. + * @throws AuthenticatorMgtException If an error occurs while updating the authenticator configuration. + */ + public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator( + UserDefinedLocalAuthenticatorConfig authenticatorConfig, String tenantDomain) + throws AuthenticatorMgtException { + + UserDefinedLocalAuthenticatorConfig existingConfig = resolveExistingAuthenticator( + authenticatorConfig.getName(), tenantDomain); + authenticatorValidator.validateDefinedByType(existingConfig.getDefinedByType()); + authenticatorValidator.validateForBlank("Display name", authenticatorConfig.getDisplayName()); + + return CACHE_BACKED_DAO.updateUserDefinedLocalAuthenticator( + existingConfig, authenticatorConfig, IdentityTenantUtil.getTenantId(tenantDomain)); + } + + /** + * Update a Local Application Authenticator configuration. + * + * @param authenticatorName Name of Local Application Authenticator configuration to be deleted. + * @param tenantDomain Tenant domain. + * @throws AuthenticatorMgtException If an error occurs while deleting the authenticator configuration. + */ + public void deleteUserDefinedLocalAuthenticator(String authenticatorName, String tenantDomain) + throws AuthenticatorMgtException { + + UserDefinedLocalAuthenticatorConfig existingConfig = resolveExistingAuthenticator( + authenticatorName, tenantDomain); + authenticatorValidator.validateDefinedByType(existingConfig.getDefinedByType()); + + CACHE_BACKED_DAO.deleteUserDefinedLocalAuthenticator(authenticatorName, existingConfig, + IdentityTenantUtil.getTenantId(tenantDomain)); + } + + /** + * Retrieve a Local Application Authenticator configuration by name. + * + * @param authenticatorName Name of Local Application Authenticator configuration to be deleted. + * @param tenantDomain Tenant domain. + * @return Retrieved UserDefinedLocalAuthenticatorConfig. + * @throws AuthenticatorMgtException If an error occurs while retrieving the authenticator configuration. + */ + public UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator(String authenticatorName, + String tenantDomain) throws AuthenticatorMgtException { + + return CACHE_BACKED_DAO.getUserDefinedLocalAuthenticator( + authenticatorName, IdentityTenantUtil.getTenantId(tenantDomain)); + } + + private UserDefinedLocalAuthenticatorConfig resolveExistingAuthenticator(String authenticatorName, + String tenantDomain) throws AuthenticatorMgtException { + + UserDefinedLocalAuthenticatorConfig existingAuthenticatorConfig = CACHE_BACKED_DAO. + getUserDefinedLocalAuthenticator(authenticatorName, IdentityTenantUtil.getTenantId(tenantDomain)); + + if (existingAuthenticatorConfig == null) { + throw buildClientException(AuthenticatorMgtError.ERROR_NOT_FOUND_AUTHENTICATOR, authenticatorName); + } + + return existingAuthenticatorConfig; + } } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/constant/AuthenticatorMgtSQLConstants.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/constant/AuthenticatorMgtSQLConstants.java new file mode 100644 index 000000000000..6269a541810b --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/constant/AuthenticatorMgtSQLConstants.java @@ -0,0 +1,86 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.constant; + +/** + * SQL constants for authenticator configuration management service. + */ +public class AuthenticatorMgtSQLConstants { + + private AuthenticatorMgtSQLConstants() { + + } + + /** + * Column Names. + */ + public static class Column { + + public static final String IDP_ID = "ID"; + public static final String IDP_NAME = "IDP_NAME"; + public static final String TENANT_ID = "TENANT_ID"; + public static final String NAME = "NAME"; + public static final String IS_ENABLED = "IS_ENABLED"; + public static final String DEFINED_BY = "DEFINED_BY"; + public static final String AUTHENTICATION_TYPE = "AUTHENTICATION_TYPE"; + public static final String DISPLAY_NAME = "DISPLAY_NAME"; + public static final String ID = "ID"; + public static final String AUTHENTICATOR_ID = "AUTHENTICATOR_ID"; + public static final String PROPERTY_KEY = "PROPERTY_KEY"; + public static final String PROPERTY_VALUE = "PROPERTY_VALUE"; + public static final String IS_SECRET = "IS_SECRET"; + + private Column() { + + } + } + + /** + * Queries. + */ + public static class Query { + + public static final String ADD_AUTHENTICATOR_SQL = "INSERT INTO IDP_AUTHENTICATOR " + + "(TENANT_ID, IDP_ID, NAME, IS_ENABLED, DEFINED_BY, AUTHENTICATION_TYPE, DISPLAY_NAME) VALUES" + + " (:TENANT_ID;, (SELECT ID FROM IDP WHERE IDP.NAME = :IDP_NAME; AND IDP.TENANT_ID = :TENANT_ID;), " + + ":NAME;, :IS_ENABLED;, :DEFINED_BY;, :AUTHENTICATION_TYPE;, :DISPLAY_NAME;);"; + public static final String UPDATE_AUTHENTICATOR_SQL = "UPDATE IDP_AUTHENTICATOR SET IS_ENABLED = " + + ":IS_ENABLED;, DISPLAY_NAME = :DISPLAY_NAME; WHERE NAME = :NAME; AND TENANT_ID = :TENANT_ID;"; + public static final String GET_AUTHENTICATOR_SQL = "SELECT * FROM IDP_AUTHENTICATOR " + + "WHERE DEFINED_BY = :DEFINED_BY; AND NAME = :NAME; AND TENANT_ID = :TENANT_ID;"; + public static final String GET_ALL_USER_DEFINED_AUTHENTICATOR_SQL = "SELECT * FROM IDP_AUTHENTICATOR " + + "WHERE DEFINED_BY = :DEFINED_BY; AND TENANT_ID = :TENANT_ID;"; + public static final String DELETE_AUTHENTICATOR_SQL = "DELETE FROM IDP_AUTHENTICATOR WHERE NAME = :NAME; " + + " AND TENANT_ID = :TENANT_ID;"; + public static final String GET_AUTHENTICATOR_ID_SQL = "SELECT ID FROM IDP_AUTHENTICATOR " + + "WHERE NAME = :NAME; AND TENANT_ID = :TENANT_ID;"; + public static final String ADD_AUTHENTICATOR_PROP_SQL = "INSERT INTO IDP_AUTHENTICATOR_PROPERTY " + + "(AUTHENTICATOR_ID, TENANT_ID, PROPERTY_KEY, PROPERTY_VALUE, IS_SECRET) VALUES " + + "(:AUTHENTICATOR_ID;, :TENANT_ID;, :PROPERTY_KEY;, :PROPERTY_VALUE;, :IS_SECRET;);"; + public static final String DELETE_AUTHENTICATOR_PROP_SQL = "DELETE FROM IDP_AUTHENTICATOR_PROPERTY " + + "WHERE AUTHENTICATOR_ID = :AUTHENTICATOR_ID; AND TENANT_ID = :TENANT_ID;"; + public static final String GET_AUTHENTICATOR_PROP_SQL = "SELECT PROPERTY_KEY, PROPERTY_VALUE, IS_SECRET" + + " FROM IDP_AUTHENTICATOR_PROPERTY " + + "WHERE AUTHENTICATOR_ID = :AUTHENTICATOR_ID; AND TENANT_ID = :TENANT_ID;"; + + private Query() { + + } + } +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtClientException.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtClientException.java new file mode 100644 index 000000000000..1542f39297fc --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtClientException.java @@ -0,0 +1,30 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.exception; + +/** + * Authenticator configuration management client exception. + */ +public class AuthenticatorMgtClientException extends AuthenticatorMgtException { + + public AuthenticatorMgtClientException(String errorCode, String message, String description) { + + super(message, description, errorCode); + } +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtException.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtException.java new file mode 100644 index 000000000000..1e2e37da3981 --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtException.java @@ -0,0 +1,63 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.exception; + +/** + * Authenticator configuration management exception. + */ +public class AuthenticatorMgtException extends Exception { + + private String errorCode; + private String description; + + public AuthenticatorMgtException(String message) { + + super(message); + } + + public AuthenticatorMgtException(String message, String errorCode, Throwable cause) { + + super(message, cause); + this.errorCode = errorCode; + } + + public AuthenticatorMgtException(String message, String description, String errorCode) { + + super(message); + this.errorCode = errorCode; + this.description = description; + } + + public AuthenticatorMgtException(String message, String description, String errorCode, Throwable cause) { + + super(message, cause); + this.errorCode = errorCode; + this.description = description; + } + + public String getErrorCode() { + + return this.errorCode; + } + + public String getDescription() { + + return this.description; + } +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtServerException.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtServerException.java new file mode 100644 index 000000000000..d70c44ab7b83 --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtServerException.java @@ -0,0 +1,36 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.exception; + +/** + * Authenticator configuration management server exception. + */ +public class AuthenticatorMgtServerException extends AuthenticatorMgtException { + + public AuthenticatorMgtServerException(String errorCode, String message, String description) { + + super(message, errorCode, description); + } + + public AuthenticatorMgtServerException(String errorCode, String message, String description, + Throwable cause) { + + super(message, description, errorCode, cause); + } +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtServerRuntimeException.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtServerRuntimeException.java new file mode 100644 index 000000000000..1c4bad60ce9d --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtServerRuntimeException.java @@ -0,0 +1,53 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.exception; + +/** + * Authenticator configuration management server runtime exception. + */ +public class AuthenticatorMgtServerRuntimeException extends RuntimeException { + + private final String errorCode; + private final String description; + private final Throwable cause; + + public AuthenticatorMgtServerRuntimeException( + String errorCode, String message, String description, Throwable cause) { + + super(message); + this.errorCode = errorCode; + this.description = description; + this.cause = cause; + } + + public String getErrorCode() { + + return this.errorCode; + } + + public String getDescription() { + + return this.description; + } + + public Throwable getCause() { + + return this.cause; + } +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/internal/ApplicationCommonServiceComponent.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/internal/ApplicationCommonServiceComponent.java new file mode 100644 index 000000000000..c5c3e818aa3e --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/internal/ApplicationCommonServiceComponent.java @@ -0,0 +1,67 @@ +package org.wso2.carbon.identity.application.common.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.osgi.service.component.annotations.Activate; +import org.osgi.service.component.annotations.Component; +import org.osgi.service.component.annotations.Reference; +import org.osgi.service.component.annotations.ReferenceCardinality; +import org.osgi.service.component.annotations.ReferencePolicy; +import org.wso2.carbon.identity.action.management.ActionManagementService; +import org.wso2.carbon.identity.application.common.ApplicationAuthenticatorService; + +/** + * OSGI service component for the Application Common Service Component. + */ +@Component( + name = "application.common.service.component", + immediate = true +) +public class ApplicationCommonServiceComponent { + + private static final Log LOG = LogFactory.getLog(ApplicationCommonServiceComponent.class); + + @Activate + protected void activate(ComponentContext context) { + + try { + BundleContext bundleCtx = context.getBundleContext(); + bundleCtx.registerService(ApplicationAuthenticatorService.class.getName(), + ApplicationAuthenticatorService.getInstance(), + null); + LOG.debug("Application Authenticator Service is activated."); + } catch (Throwable e) { + LOG.error("Error while initializing Application Authenticator Service component.", e); + } + } + + @Reference( + name = "action.management.service", + service = ActionManagementService.class, + cardinality = ReferenceCardinality.MANDATORY, + policy = ReferencePolicy.DYNAMIC, + unbind = "unsetActionManagementService" + ) + protected void setActionManagementService(ActionManagementService actionManagementService) { + + if (LOG.isDebugEnabled()) { + LOG.debug( + "Registering a reference for ActionManagementService in the ApplicationCommonServiceComponent."); + } + ApplicationCommonServiceDataHolder.getInstance().setActionManagementService(actionManagementService); + } + + protected void unsetActionManagementService(ActionManagementService actionManagementService) { + + if (LOG.isDebugEnabled()) { + LOG.debug("Unregistering the reference for ActionManagementService in the " + + "ApplicationCommonServiceComponent."); + } + if (ApplicationCommonServiceDataHolder.getInstance().getActionManagementService() + .equals(actionManagementService)) { + ApplicationCommonServiceDataHolder.getInstance().setActionManagementService(null); + } + } +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/internal/ApplicationCommonServiceDataHolder.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/internal/ApplicationCommonServiceDataHolder.java new file mode 100644 index 000000000000..7c333500324a --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/internal/ApplicationCommonServiceDataHolder.java @@ -0,0 +1,65 @@ +package org.wso2.carbon.identity.application.common.internal; + +import org.wso2.carbon.identity.action.management.ActionManagementService; +import org.wso2.carbon.identity.application.common.ApplicationAuthenticatorService; + +/** + * The data holder for the Application Common Service Component. + */ +public class ApplicationCommonServiceDataHolder { + + private static final ApplicationCommonServiceDataHolder INSTANCE = new ApplicationCommonServiceDataHolder(); + + private ActionManagementService actionManagementService; + private ApplicationAuthenticatorService applicationAuthenticatorService; + + /** + * Get the instance of the ApplicationCommonServiceDataHolder. + * + * @return ApplicationCommonServiceDataHolder instance. + */ + public static ApplicationCommonServiceDataHolder getInstance() { + + return INSTANCE; + } + + /** + * Get the ActionManagementService. + * + * @return ActionManagementService instance. + */ + public ActionManagementService getActionManagementService() { + + return actionManagementService; + } + + /** + * Set the ActionManagementService. + * + * @param actionManagementService ActionManagementService instance. + */ + public void setActionManagementService(ActionManagementService actionManagementService) { + + this.actionManagementService = actionManagementService; + } + + /** + * Get the ApplicationAuthenticatorService. + * + * @return ApplicationAuthenticatorService instance. + */ + public ApplicationAuthenticatorService getApplicationAuthenticatorService() { + + return applicationAuthenticatorService; + } + + /** + * Set the ApplicationAuthenticatorService. + * + * @param applicationAuthenticatorService ApplicationAuthenticatorService instance. + */ + public void setApplicationAuthenticatorService(ApplicationAuthenticatorService applicationAuthenticatorService) { + + this.applicationAuthenticatorService = applicationAuthenticatorService; + } +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/model/UserDefinedFederatedAuthenticatorConfig.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/model/UserDefinedFederatedAuthenticatorConfig.java index c7fc749a3718..9bffc4544a34 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/model/UserDefinedFederatedAuthenticatorConfig.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/model/UserDefinedFederatedAuthenticatorConfig.java @@ -36,7 +36,7 @@ public UserDefinedFederatedAuthenticatorConfig() { } /** - * Get the endpoint configurations of the User defined federated authenticator config. + * Get the endpoint configurations of the user defined federated authenticator config. * * @return UserDefinedAuthenticatorEndpointConfig */ @@ -46,9 +46,9 @@ public UserDefinedAuthenticatorEndpointConfig getEndpointConfig() { } /** - * Set the endpoint configurations of the User defined federated authenticator config. + * Set the endpoint configurations of the user defined federated authenticator config. * - * @param endpointConfig The endpoint config of the User defined federated authenticator config. + * @param endpointConfig The endpoint config of the user defined federated authenticator config. */ public void setEndpointConfig(UserDefinedAuthenticatorEndpointConfig endpointConfig) { diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/model/UserDefinedLocalAuthenticatorConfig.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/model/UserDefinedLocalAuthenticatorConfig.java index fab5a37a69bd..53f8c68644b2 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/model/UserDefinedLocalAuthenticatorConfig.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/model/UserDefinedLocalAuthenticatorConfig.java @@ -28,11 +28,13 @@ public class UserDefinedLocalAuthenticatorConfig extends LocalAuthenticatorConfi private static final String TAG_2FA = "2FA"; private static final String TAG_CUSTOM = "CUSTOM"; + private AuthenticationType authenticationType; protected UserDefinedAuthenticatorEndpointConfig endpointConfig; public UserDefinedLocalAuthenticatorConfig(AuthenticationType type) { + authenticationType = type; definedByType = DefinedByType.USER; if (AuthenticationType.VERIFICATION == type) { setTags(new String[]{TAG_CUSTOM, TAG_2FA}); @@ -42,7 +44,7 @@ public UserDefinedLocalAuthenticatorConfig(AuthenticationType type) { } /** - * Get the endpoint configurations of the User defined local authenticator config. + * Get the endpoint configurations of the user defined local authenticator config. * * @return UserDefinedAuthenticatorEndpointConfig */ @@ -52,12 +54,32 @@ public UserDefinedAuthenticatorEndpointConfig getEndpointConfig() { } /** - * Set the endpoint configurations of the User defined local authenticator config. + * Set the endpoint configurations of the user defined local authenticator config. * - * @param endpointConfig The endpoint config of the User defined local authenticator config. + * @param endpointConfig The endpoint config of the user defined local authenticator config. */ public void setEndpointConfig(UserDefinedAuthenticatorEndpointConfig endpointConfig) { this.endpointConfig = endpointConfig; } + + /** + * Get the authentication type of the user defined local authenticator config. + * + * @return AuthenticationType. + */ + public AuthenticationType getAuthenticationType() { + + return authenticationType; + } + + /** + * Set the authentication type of the user defined local authenticator config. + * + * @param authenticationType The authentication type of the user defined local authenticator config. + */ + public void setAuthenticationType(AuthenticationType authenticationType) { + + this.authenticationType = authenticationType; + } } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/AuthenticatorMgtExceptionBuilder.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/AuthenticatorMgtExceptionBuilder.java new file mode 100644 index 000000000000..e52cddb4baed --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/AuthenticatorMgtExceptionBuilder.java @@ -0,0 +1,144 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.util; + +import org.apache.commons.lang.ArrayUtils; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtClientException; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtServerException; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtServerRuntimeException; + +/** + * Utility class for building authenticator management exceptions. + */ +public class AuthenticatorMgtExceptionBuilder { + + private AuthenticatorMgtExceptionBuilder() { + + } + + public static AuthenticatorMgtClientException buildClientException(AuthenticatorMgtError error, String... data) { + + String description = error.getDescription(); + if (ArrayUtils.isNotEmpty(data)) { + description = String.format(description, data); + } + + return new AuthenticatorMgtClientException(error.getCode(), error.getMessage(), description); + } + + public static AuthenticatorMgtServerException buildServerException(AuthenticatorMgtError error, String... data) { + + String description = error.getDescription(); + if (ArrayUtils.isNotEmpty(data)) { + description = String.format(description, data); + } + + return new AuthenticatorMgtServerException(error.getCode(), error.getMessage(), description); + } + + public static AuthenticatorMgtServerException buildServerException(AuthenticatorMgtError error, Throwable e, + String... data) { + + String description = error.getDescription(); + if (ArrayUtils.isNotEmpty(data)) { + description = String.format(description, data); + } + + return new AuthenticatorMgtServerException(error.getCode(), error.getMessage(), description, e); + } + + public static AuthenticatorMgtServerRuntimeException buildRuntimeServerException(AuthenticatorMgtError error, + Throwable e, String... data) { + + String description = error.getDescription(); + if (ArrayUtils.isNotEmpty(data)) { + description = String.format(description, data); + } + + return new AuthenticatorMgtServerRuntimeException(error.getCode(), error.getMessage(), description, e); + } + + /** + * Enum class to represent the rule metadata errors. + */ + public enum AuthenticatorMgtError { + + // Client errors. + ERROR_NOT_FOUND_AUTHENTICATOR("60001", "No Authenticator found.", + "No Authenticator found by given authenticator name: %s."), + ERROR_OP_ON_SYSTEM_AUTHENTICATOR("60002", "No operations allowed on system authenticators.", + "Do not allow to perform any operation on system defined authenticator: %s."), + ERROR_AUTHENTICATOR_ALREADY_EXIST("60003", "The authenticator already exists.", + "The authenticator already exists for the given name: %s."), + ERROR_INVALID_AUTHENTICATOR_NAME("60004", "Authenticator name is invalid.", + "The provided authenticator name %s is not in the expected format %s."), + ERROR_BLANK_FIELD_VALUE("60004", "Invalid empty or blank value.", + "Value for %s should not be empty or blank."), + + // Server errors. + ERROR_WHILE_ADDING_AUTHENTICATOR("65001", "Error while adding authenticator.", + "Error while persisting authenticator to the system."), + ERROR_WHILE_UPDATING_AUTHENTICATOR("65002", "Error while updating authenticator.", + "Error while updating authenticator in the system."), + ERROR_WHILE_RETRIEVING_AUTHENTICATOR_BY_NAME("65003", "Error while retrieving authenticator.", + "Error while retrieving authenticator in the system."), + ERROR_WHILE_DELETING_AUTHENTICATOR("65004", "Error while deleting authenticator.", + "Error while deleting authenticator in the system."), + ERROR_CODE_INVALID_DEFINED_BY_AUTH_PROVIDED("65005", "Error while adding local authenticator.", + "Only system defined authenticators are allowed to add via this method."), + ERROR_CODE_NO_AUTHENTICATOR_FOUND("65006", "No authenticator found.", + "No authenticator found by given authenticator name: %s."), + ERROR_CODE_NO_ACTION_ID_FOUND("65007", "No action id found.", + "No action id found for the authenticator: %s."), + ERROR_CODE_ADDING_ENDPOINT_CONFIG("65008", "Error while adding endpoint configurations.", + "Error while adding endpoint configurations for the user defined local authenticator %s."), + ERROR_CODE_UPDATING_ENDPOINT_CONFIG("65009", "Error while updating endpoint configurations.", + "Error while updating endpoint configurations for the user defined local authenticator %s."), + ERROR_CODE_RETRIEVING_ENDPOINT_CONFIG("65010", "Error while resolving endpoint configurations.", + "Error while retrieving endpoint configurations for the user defined local authenticator %s."), + ERROR_CODE_DELETING_ENDPOINT_CONFIG("65011", "Error while managing endpoint configurations.", + "Error while managing endpoint configurations for the user defined local authenticator %s."); + + private final String code; + private final String message; + private final String description; + + AuthenticatorMgtError(String code, String message, String description) { + + this.code = code; + this.message = message; + this.description = description; + } + + public String getCode() { + + return code; + } + + public String getMessage() { + + return message; + } + + public String getDescription() { + + return description; + } + } +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedAuthenticatorEndpointConfigManager.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedAuthenticatorEndpointConfigManager.java new file mode 100644 index 000000000000..12fb7dbe7006 --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedAuthenticatorEndpointConfigManager.java @@ -0,0 +1,191 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.util; + +import org.wso2.carbon.identity.action.management.exception.ActionMgtException; +import org.wso2.carbon.identity.action.management.model.Action; +import org.wso2.carbon.identity.action.management.model.EndpointConfig; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtServerException; +import org.wso2.carbon.identity.application.common.internal.ApplicationCommonServiceDataHolder; +import org.wso2.carbon.identity.application.common.model.Property; +import org.wso2.carbon.identity.application.common.model.UserDefinedAuthenticatorEndpointConfig; +import org.wso2.carbon.identity.application.common.model.UserDefinedLocalAuthenticatorConfig; +import org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.AuthenticatorMgtError; +import org.wso2.carbon.identity.core.util.IdentityTenantUtil; + +import java.util.Arrays; +import java.util.HashMap; +import java.util.Map; + +import static org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.buildServerException; + +/** + * This class responsible for managing authenticator endpoint configurations for the user defined Local + * authenticators. + */ +public class UserDefinedAuthenticatorEndpointConfigManager { + + private static final String ACTION_ID_PROPERTY = "actionId"; + + /** + * Create a new action for given endpoint configurations of the user defined authenticator. + * + * @param config The Local application authenticator configuration. + * @param tenantId The id of Tenant domain. + * @throws AuthenticatorMgtServerException If an error occurs while adding the action. + */ + public void addEndpointConfigurations(UserDefinedLocalAuthenticatorConfig config, int tenantId) + throws AuthenticatorMgtServerException { + + try { + Action action = ApplicationCommonServiceDataHolder.getInstance().getActionManagementService() + .addAction(Action.ActionTypes.AUTHENTICATION.getPathParam(), + buildActionToCreate(config.getName(), config.getEndpointConfig().getEndpointConfig()), + IdentityTenantUtil.getTenantDomain(tenantId)); + Property endpointProperty = new Property(); + endpointProperty.setName(ACTION_ID_PROPERTY); + endpointProperty.setValue(action.getId()); + config.setProperties(new Property[]{endpointProperty}); + } catch (ActionMgtException e) { + throw buildServerException(AuthenticatorMgtError.ERROR_CODE_ADDING_ENDPOINT_CONFIG, e, config.getName()); + } + } + + /** + * Updated associated action for given updated endpoint configurations of the user defined authenticator. + * + * @param newConfig The Local application authenticator configuration to be updated. + * @param oldConfig The current Local application authenticator configuration. + * @param tenantId The id of Tenant domain. + * @throws AuthenticatorMgtServerException If an error occurs while updating associated action. + */ + public void updateEndpointConfigurations(UserDefinedLocalAuthenticatorConfig newConfig, + UserDefinedLocalAuthenticatorConfig oldConfig, int tenantId) + throws AuthenticatorMgtServerException { + + String actionId = getActionIdFromProperty(oldConfig.getProperties(), oldConfig.getName()); + try { + ApplicationCommonServiceDataHolder.getInstance().getActionManagementService() + .updateAction(Action.ActionTypes.AUTHENTICATION.getPathParam(), + actionId, + buildActionToUpdate(newConfig.getEndpointConfig().getEndpointConfig()), + IdentityTenantUtil.getTenantDomain(tenantId)); + newConfig.setProperties(oldConfig.getProperties()); + } catch (ActionMgtException e) { + throw buildServerException(AuthenticatorMgtError.ERROR_CODE_UPDATING_ENDPOINT_CONFIG, e, + actionId, oldConfig.getName()); + } + } + + /** + * Retrieve associated action of the user defined authenticator. + * + * @param config The Local application authenticator configuration. + * @param tenantId The id of Tenant domain. + * @return Local authenticator with endpoint configurations resolved. + * @throws AuthenticatorMgtServerException If an error occurs retrieving updating associated action. + */ + public UserDefinedLocalAuthenticatorConfig resolveEndpointConfigurations(UserDefinedLocalAuthenticatorConfig config, + int tenantId) throws AuthenticatorMgtServerException { + + if (config == null) { + return null; + } + String actionId = getActionIdFromProperty(config.getProperties(), config.getName()); + try { + Action action = ApplicationCommonServiceDataHolder.getInstance().getActionManagementService() + .getActionByActionId(Action.ActionTypes.AUTHENTICATION.getPathParam(), + actionId, + IdentityTenantUtil.getTenantDomain(tenantId)); + + config.setEndpointConfig(buildUserDefinedAuthenticatorEndpointConfig(action.getEndpoint())); + return config; + } catch (ActionMgtException e) { + throw buildServerException(AuthenticatorMgtError.ERROR_CODE_RETRIEVING_ENDPOINT_CONFIG, e, + actionId, config.getName()); + } + } + + private UserDefinedAuthenticatorEndpointConfig buildUserDefinedAuthenticatorEndpointConfig( + EndpointConfig endpointConfig) { + + UserDefinedAuthenticatorEndpointConfig.UserDefinedAuthenticatorEndpointConfigBuilder endpointConfigBuilder = + new UserDefinedAuthenticatorEndpointConfig.UserDefinedAuthenticatorEndpointConfigBuilder(); + endpointConfigBuilder.uri(endpointConfig.getUri()); + endpointConfigBuilder.authenticationType(endpointConfig.getAuthentication().getType().getName()); + Map propMap = new HashMap<>(); + endpointConfig.getAuthentication().getProperties() + .forEach(prop -> propMap.put(prop.getName(), prop.getValue())); + endpointConfigBuilder.authenticationProperties(propMap); + return endpointConfigBuilder.build(); + } + + /** + * Delete associated action of the user defined authenticator. + * + * @param config The Local application authenticator configuration. + * @param tenantId The id of Tenant domain. + * + * @throws AuthenticatorMgtServerException If an error occurs while deleting associated action. + */ + public void deleteEndpointConfigurations(UserDefinedLocalAuthenticatorConfig config, int tenantId) throws + AuthenticatorMgtServerException { + + String actionId = getActionIdFromProperty(config.getProperties(), config.getName()); + try { + ApplicationCommonServiceDataHolder.getInstance().getActionManagementService() + .deleteAction(Action.ActionTypes.AUTHENTICATION.getPathParam(), + actionId, + IdentityTenantUtil.getTenantDomain(tenantId)); + } catch (ActionMgtException e) { + throw buildServerException(AuthenticatorMgtError.ERROR_CODE_DELETING_ENDPOINT_CONFIG, e, + actionId, config.getName()); + } + } + + private Action buildActionToCreate(String authenticatorName, EndpointConfig endpointConfig) { + + Action.ActionRequestBuilder actionRequestBuilder = new Action.ActionRequestBuilder(); + actionRequestBuilder.name(authenticatorName); + actionRequestBuilder.description(String.format("This is the action associated to the user defined Local" + + "authenticator %s.", authenticatorName)); + actionRequestBuilder.endpoint(endpointConfig); + + return actionRequestBuilder.build(); + } + + private Action buildActionToUpdate(EndpointConfig endpointConfig) { + + Action.ActionRequestBuilder actionRequestBuilder = new Action.ActionRequestBuilder(); + actionRequestBuilder.endpoint(endpointConfig); + + return actionRequestBuilder.build(); + } + + private String getActionIdFromProperty(Property[] properties, String authenticatorName) + throws AuthenticatorMgtServerException { + + return Arrays.stream(properties) + .filter(property -> ACTION_ID_PROPERTY.equals(property.getName())) + .map(Property::getValue) + .findFirst() + .orElseThrow(() -> buildServerException(AuthenticatorMgtError.ERROR_CODE_NO_ACTION_ID_FOUND, + authenticatorName)); + } +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedLocalAuthenticatorValidator.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedLocalAuthenticatorValidator.java new file mode 100644 index 000000000000..a457c1d49f91 --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedLocalAuthenticatorValidator.java @@ -0,0 +1,80 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.util; + +import org.apache.commons.lang.StringUtils; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtClientException; +import org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.AuthenticatorMgtError; +import org.wso2.carbon.identity.base.AuthenticatorPropertyConstants.DefinedByType; + +import java.util.regex.Pattern; + +import static org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.buildClientException; + +/** + * User Defined Local Authenticator Validator class. + */ +public class UserDefinedLocalAuthenticatorValidator { + + private static final String AUTHENTICATOR_NAME_REGEX = "^[a-zA-Z0-9][a-zA-Z0-9-_]*$"; + private final Pattern authenticatorNameRegexPattern = Pattern.compile(AUTHENTICATOR_NAME_REGEX); + + /** + * Validate whether required fields exist. + * + * @param fieldName Field name. + * @param fieldValue Field value. + * @throws AuthenticatorMgtClientException if the provided field is empty. + */ + public void validateForBlank(String fieldName, String fieldValue) throws AuthenticatorMgtClientException { + + if (StringUtils.isBlank(fieldValue)) { + throw buildClientException(AuthenticatorMgtError.ERROR_BLANK_FIELD_VALUE, fieldName); + } + } + + /** + * Validate the user defined local authenticator name. + * + * @param name The authenticator name. + * @throws AuthenticatorMgtClientException if the authenticator name is not valid. + */ + public void validateAuthenticatorName(String name) throws AuthenticatorMgtClientException { + + boolean isValidName = authenticatorNameRegexPattern.matcher(name).matches(); + if (!isValidName) { + throw buildClientException(AuthenticatorMgtError.ERROR_INVALID_AUTHENTICATOR_NAME, + name, AUTHENTICATOR_NAME_REGEX); + } + } + + /** + * Validate the authenticator is a user defined by authenticator. + * + * @param definedByType The defined by type of the authenticator config. + * @throws AuthenticatorMgtClientException if the authenticator is not a user defined authenticator. + */ + public void validateDefinedByType(DefinedByType definedByType) + throws AuthenticatorMgtClientException { + + if (definedByType != DefinedByType.USER) { + throw buildClientException(AuthenticatorMgtError.ERROR_OP_ON_SYSTEM_AUTHENTICATOR); + } + } +} From 26d5dfd5b7f7b8e37b5c8fada0bc5914e08f7b58 Mon Sep 17 00:00:00 2001 From: Thisara-Welmilla Date: Tue, 3 Dec 2024 22:47:24 +0530 Subject: [PATCH 03/15] Add unit tests for user def auth mgt. --- .../ApplicationAuthenticatorServiceTest.java | 412 +++++ .../model/test/util/ActionMgtTestUtil.java | 96 ++ .../src/test/resources/dbscripts/h2.sql | 1482 +++++++++++++++++ .../test/resources/repository/conf/carbon.xml | 686 ++++++++ .../repository/conf/identity/identity.xml | 743 +++++++++ .../src/test/resources/testng.xml | 1 + 6 files changed, 3420 insertions(+) create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/util/ActionMgtTestUtil.java create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/dbscripts/h2.sql create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/repository/conf/carbon.xml create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/repository/conf/identity/identity.xml diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java new file mode 100644 index 000000000000..b54d245727ef --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java @@ -0,0 +1,412 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.model.test; + +import org.mockito.MockedStatic; +import org.testng.Assert; +import org.testng.annotations.AfterMethod; +import org.testng.annotations.BeforeClass; +import org.testng.annotations.DataProvider; +import org.testng.annotations.Test; +import org.wso2.carbon.identity.action.management.ActionManagementService; +import org.wso2.carbon.identity.action.management.exception.ActionMgtException; +import org.wso2.carbon.identity.action.management.model.Action; +import org.wso2.carbon.identity.action.management.model.Authentication; +import org.wso2.carbon.identity.action.management.model.EndpointConfig; +import org.wso2.carbon.identity.application.common.ApplicationAuthenticatorService; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtException; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtServerRuntimeException; +import org.wso2.carbon.identity.application.common.internal.ApplicationCommonServiceDataHolder; +import org.wso2.carbon.identity.application.common.model.LocalAuthenticatorConfig; +import org.wso2.carbon.identity.application.common.model.Property; +import org.wso2.carbon.identity.application.common.model.UserDefinedAuthenticatorEndpointConfig.UserDefinedAuthenticatorEndpointConfigBuilder; +import org.wso2.carbon.identity.application.common.model.UserDefinedLocalAuthenticatorConfig; +import org.wso2.carbon.identity.application.common.model.test.util.ActionMgtTestUtil; +import org.wso2.carbon.identity.base.AuthenticatorPropertyConstants.AuthenticationType; +import org.wso2.carbon.identity.base.AuthenticatorPropertyConstants.DefinedByType; +import org.wso2.carbon.identity.common.testng.WithAxisConfiguration; +import org.wso2.carbon.identity.common.testng.WithCarbonHome; +import org.wso2.carbon.identity.common.testng.WithH2Database; +import org.wso2.carbon.identity.common.testng.WithRealmService; +import org.wso2.carbon.identity.common.testng.WithRegistry; +import org.wso2.carbon.identity.core.internal.IdentityCoreServiceDataHolder; +import org.wso2.carbon.identity.core.util.IdentityDatabaseUtil; + +import java.util.Arrays; +import java.util.HashMap; +import java.util.List; + +import static org.junit.Assert.assertThrows; +import static org.mockito.ArgumentMatchers.any; +import static org.mockito.ArgumentMatchers.anyString; +import static org.mockito.Mockito.doNothing; +import static org.mockito.Mockito.doThrow; +import static org.mockito.Mockito.mock; +import static org.mockito.Mockito.when; + +/** + * This class is a test suite for the ApplicationAuthenticatorServiceTest class. + * It contains unit tests to verify the functionality of the methods + * in the ApplicationAuthenticatorServiceTest class. + */ +@WithAxisConfiguration +@WithCarbonHome +@WithH2Database(files = {"dbscripts/h2.sql"}) +@WithRegistry +@WithRealmService(injectToSingletons = {IdentityCoreServiceDataHolder.class}) +public class ApplicationAuthenticatorServiceTest { + + private MockedStatic identityDatabaseUtil; + private String tenantDomain; + + private UserDefinedLocalAuthenticatorConfig authenticatorConfig1; + private UserDefinedLocalAuthenticatorConfig authenticatorConfig2; + private UserDefinedLocalAuthenticatorConfig authenticatorConfigForException; + private UserDefinedLocalAuthenticatorConfig nonExistAuthenticatorConfig; + private LocalAuthenticatorConfig systemAuthenticatorConfig; + + private ActionManagementService actionManagementService; + private static Action action; + private static EndpointConfig endpointConfig; + private static EndpointConfig endpointConfigToBeUpdated; + + private static final String AUTHENTICATOR1_NAME = "auth1"; + private static final String AUTHENTICATOR2_NAME = "auth2"; + private static final String AUTHENTICATOR_CONFIG_FOR_EXCEPTION_NAME = "exception_auth"; + private static final String NON_EXIST_AUTHENTICATOR_NAME = "non_exist_auth"; + private static final String SYSTEM_AUTHENTICATOR_NAME = "system_auth"; + + @BeforeClass + public void setUpClass() throws Exception { + + tenantDomain = "carbon.super"; + systemAuthenticatorConfig = createSystemDefinedAuthenticatorConfig(SYSTEM_AUTHENTICATOR_NAME); + authenticatorConfig1 = createUserDefinedAuthenticatorConfig(AUTHENTICATOR1_NAME, + AuthenticationType.IDENTIFICATION); + authenticatorConfig2 = createUserDefinedAuthenticatorConfig(AUTHENTICATOR2_NAME, + AuthenticationType.VERIFICATION); + nonExistAuthenticatorConfig = createUserDefinedAuthenticatorConfig(NON_EXIST_AUTHENTICATOR_NAME, + AuthenticationType.IDENTIFICATION); + authenticatorConfigForException = createUserDefinedAuthenticatorConfig(AUTHENTICATOR_CONFIG_FOR_EXCEPTION_NAME, + AuthenticationType.IDENTIFICATION); + + endpointConfig = ActionMgtTestUtil.createEndpointConfig("http://localhost", "admin", "admin"); + endpointConfigToBeUpdated = ActionMgtTestUtil.createEndpointConfig( + "http://localhost1", "admin1", "admin1"); + action = ActionMgtTestUtil.createAction(endpointConfig); + actionManagementService = mock(ActionManagementService.class); + + when(actionManagementService.addAction(anyString(), any(), any())).thenReturn(action); + when(actionManagementService.updateAction(anyString(), any(), any(), any())).thenReturn(action); + when(actionManagementService.getActionByActionId(anyString(), any(), any())).thenReturn(action); + doNothing().when(actionManagementService).deleteAction(anyString(), any(), any()); + + ApplicationCommonServiceDataHolder.getInstance().setApplicationAuthenticatorService( + ApplicationAuthenticatorService.getInstance()); + ApplicationCommonServiceDataHolder.getInstance().setActionManagementService(actionManagementService); + } + + @AfterMethod + public void tearDown() { + + ApplicationCommonServiceDataHolder.getInstance().setActionManagementService(actionManagementService); + } + + @DataProvider(name = "authenticatorConfigForCreation") + public Object[][] authenticatorConfigForCreation() { + + return new Object[][]{ + {authenticatorConfig1}, + {authenticatorConfig2} + }; + } + + @Test(priority = 1, dataProvider = "authenticatorConfigForCreation") + public void testCreateUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticatorConfig config) + throws AuthenticatorMgtException { + + UserDefinedLocalAuthenticatorConfig createdAuthenticator = ApplicationCommonServiceDataHolder.getInstance() + .getApplicationAuthenticatorService().addUserDefinedLocalAuthenticator(config, tenantDomain); + + Assert.assertEquals(createdAuthenticator.getName(), config.getName()); + Assert.assertEquals(createdAuthenticator.getDisplayName(), config.getDisplayName()); + Assert.assertEquals(createdAuthenticator.isEnabled(), config.isEnabled()); + Assert.assertEquals(createdAuthenticator.getDefinedByType(), DefinedByType.USER); + if (AuthenticationType.VERIFICATION == config.getAuthenticationType()) { + Assert.assertTrue(Arrays.asList(createdAuthenticator.getTags()).contains("2FA"), + "Tag list does not contain 2FA tag for verification authentication type."); + } + Assert.assertEquals(createdAuthenticator.getProperties().length, config.getProperties().length); + } + + @Test(priority = 2, dataProvider = "authenticatorConfigForCreation", expectedExceptions = + AuthenticatorMgtException.class, expectedExceptionsMessageRegExp = "The authenticator already exists.") + public void testCreateUserDefinedLocalAuthenticatorWithExistingAuthenticator( + UserDefinedLocalAuthenticatorConfig config) throws AuthenticatorMgtException { + + ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() + .addUserDefinedLocalAuthenticator(config, tenantDomain); + } + + @Test(priority = 3, expectedExceptions = AuthenticatorMgtException.class, + expectedExceptionsMessageRegExp = "Invalid empty or blank value.") + public void testCreateUserDefinedLocalAuthenticatorWithBlankDisplayName() throws AuthenticatorMgtException { + + UserDefinedLocalAuthenticatorConfig config = createUserDefinedAuthenticatorConfig("withBlankDisplayName", + AuthenticationType.IDENTIFICATION); + config.setDisplayName(""); + ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() + .addUserDefinedLocalAuthenticator(config, tenantDomain); + } + + @Test(priority = 3, expectedExceptions = AuthenticatorMgtException.class, + expectedExceptionsMessageRegExp = "Authenticator name is invalid.") + public void testCreateUserDefinedLocalAuthenticatorWithInvalidName() throws AuthenticatorMgtException { + + ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() + .addUserDefinedLocalAuthenticator(createUserDefinedAuthenticatorConfig("323#2@dwd", + AuthenticationType.IDENTIFICATION), tenantDomain); + } + + @Test(priority = 4) + public void testAddIdPActionException() throws Exception { + + ActionManagementService actionManagementServiceForException = mock(ActionManagementService.class); + when(actionManagementServiceForException.addAction(anyString(), any(), any())) + .thenThrow(ActionMgtException.class); + ApplicationCommonServiceDataHolder.getInstance().setActionManagementService( + actionManagementServiceForException); + + assertThrows(AuthenticatorMgtException.class, () -> + ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() + .addUserDefinedLocalAuthenticator(authenticatorConfigForException, tenantDomain)); + } + + @Test(priority = 5) + public void testAddLocalAuthenticator() { + + ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() + .addLocalAuthenticator(systemAuthenticatorConfig); + Assert.assertNotNull(ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() + .getLocalAuthenticatorByName(SYSTEM_AUTHENTICATOR_NAME)); + } + + @Test(priority = 6) + public void testAddLocalAuthenticatorWithRuntimeError() { + + assertThrows(AuthenticatorMgtServerRuntimeException.class, () -> + ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() + .addLocalAuthenticator(authenticatorConfig1)); + } + + @Test(priority = 10) + public void testGetAllUserDefinedLocalAuthenticators() throws Exception { + + List authenticatorsList = ApplicationCommonServiceDataHolder.getInstance() + .getApplicationAuthenticatorService().getAllUserDefinedLocalAuthenticators(tenantDomain); + Assert.assertEquals(authenticatorsList.size(), 2); + } + + @DataProvider(name = "authenticatorConfigToModify") + public Object[][] authenticatorConfigToModify() { + + authenticatorConfig1.setDisplayName("Updated Display Name"); + + authenticatorConfig2.setEnabled(false); + authenticatorConfig2.setDefinedByType(DefinedByType.SYSTEM); + + return new Object[][]{ + {authenticatorConfig1}, + {authenticatorConfig2} + }; + } + + @Test(priority = 10) + public void testGetUserDefinedAuthenticator() throws Exception { + + UserDefinedLocalAuthenticatorConfig authenticator = ApplicationCommonServiceDataHolder.getInstance() + .getApplicationAuthenticatorService().getUserDefinedLocalAuthenticator( + authenticatorConfig1.getName(), tenantDomain); + Assert.assertNotNull(authenticator); + } + + @Test(priority = 11) + public void testGetUserDefinedAuthenticatorWithActionException() throws Exception { + + ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() + .addUserDefinedLocalAuthenticator(authenticatorConfigForException, tenantDomain); + ActionManagementService actionManagementServiceForException = mock(ActionManagementService.class); + when(actionManagementServiceForException.addAction(anyString(), any(), any())).thenReturn(action); + when(actionManagementServiceForException.getActionByActionId(anyString(), any(), any())) + .thenThrow(ActionMgtException.class); + ApplicationCommonServiceDataHolder.getInstance().setActionManagementService( + actionManagementServiceForException); + } + + @Test(priority = 20, dataProvider = "authenticatorConfigToModify") + public void testUpdateUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticatorConfig config) + throws AuthenticatorMgtException { + + UserDefinedLocalAuthenticatorConfig updatedAuthenticator = ApplicationCommonServiceDataHolder.getInstance() + .getApplicationAuthenticatorService().updateUserDefinedLocalAuthenticator(config, tenantDomain); + + Assert.assertEquals(updatedAuthenticator.getName(), config.getName()); + Assert.assertEquals(updatedAuthenticator.getDisplayName(), config.getDisplayName()); + Assert.assertEquals(updatedAuthenticator.isEnabled(), config.isEnabled()); + Assert.assertEquals(updatedAuthenticator.getDefinedByType(), DefinedByType.USER); + Assert.assertEquals(updatedAuthenticator.getProperties().length, config.getProperties().length); + } + + @Test(priority = 21, expectedExceptions = AuthenticatorMgtException.class, + expectedExceptionsMessageRegExp = "No Authenticator found.") + public void testUpdateUserDefinedLocalAuthenticatorWithNonExistingAuthenticator() throws AuthenticatorMgtException { + + ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() + .updateUserDefinedLocalAuthenticator(nonExistAuthenticatorConfig, tenantDomain); + } + + @Test(priority = 22) + public void testUpdateIdPActionException() throws Exception { + + ActionManagementService actionManagementServiceForException = mock(ActionManagementService.class); + when(actionManagementServiceForException.updateAction(any(), any(), any(), any())) + .thenThrow(ActionMgtException.class); + when(actionManagementServiceForException.getActionByActionId(anyString(), any(), any())).thenReturn(action); + ApplicationCommonServiceDataHolder.getInstance().setActionManagementService( + actionManagementServiceForException); + + assertThrows(AuthenticatorMgtException.class, () -> ApplicationCommonServiceDataHolder.getInstance() + .getApplicationAuthenticatorService().updateUserDefinedLocalAuthenticator( + authenticatorConfigForException, tenantDomain)); + } + + @DataProvider(name = "authenticatorConfigToRetrieve") + public Object[][] authenticatorConfigToRetrieve() { + + return new Object[][]{ + {authenticatorConfig1, authenticatorConfig1, AuthenticationType.IDENTIFICATION.toString()}, + {authenticatorConfig2, authenticatorConfig2, AuthenticationType.VERIFICATION.toString()}, + {nonExistAuthenticatorConfig, null, null} + }; + } + + @Test(priority = 27, dataProvider = "authenticatorConfigToRetrieve") + public void testGetUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticatorConfig configToBeRetrieved, + UserDefinedLocalAuthenticatorConfig expectedConfig, String type) throws AuthenticatorMgtException { + + UserDefinedLocalAuthenticatorConfig retrievedConfig = ApplicationCommonServiceDataHolder.getInstance() + .getApplicationAuthenticatorService().getUserDefinedLocalAuthenticator( + configToBeRetrieved.getName(), tenantDomain); + Assert.assertEquals(retrievedConfig, expectedConfig); + if (expectedConfig != null) { + Assert.assertEquals(retrievedConfig.getDisplayName(), expectedConfig.getDisplayName()); + Assert.assertEquals(retrievedConfig.isEnabled(), expectedConfig.isEnabled()); + Assert.assertEquals(retrievedConfig.getDefinedByType(), DefinedByType.USER); + if (AuthenticationType.VERIFICATION.toString().equals(type)) { + Assert.assertTrue(Arrays.asList(retrievedConfig.getTags()).contains("2FA"), + "Tag list does not contain 2FA tag for verification authentication type."); + } + Assert.assertEquals(retrievedConfig.getProperties().length, expectedConfig.getProperties().length); + } + } + + @Test(priority = 40) + public void testDeleteUserDefinedLocalAuthenticatorWithActionException() throws Exception { + + ActionManagementService actionManagementServiceForException = mock(ActionManagementService.class); + doThrow(ActionMgtException.class).when(actionManagementServiceForException).deleteAction(any(), any(), any()); + when(actionManagementServiceForException.getActionByActionId(anyString(), any(), any())).thenReturn(action); + ApplicationCommonServiceDataHolder.getInstance() + .setActionManagementService(actionManagementServiceForException); + + assertThrows(AuthenticatorMgtException.class, () -> ApplicationCommonServiceDataHolder.getInstance(). + getApplicationAuthenticatorService().deleteUserDefinedLocalAuthenticator( + authenticatorConfigForException.getName(), tenantDomain)); + Assert.assertNotNull(ApplicationCommonServiceDataHolder.getInstance(). + getApplicationAuthenticatorService().getUserDefinedLocalAuthenticator( + authenticatorConfigForException.getName(), tenantDomain)); + } + + @Test(priority = 50, dataProvider = "authenticatorConfigToModify") + public void testDeleteUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticatorConfig config) + throws AuthenticatorMgtException { + + ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() + .deleteUserDefinedLocalAuthenticator(config.getName(), tenantDomain); + Assert.assertNull(ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() + .getLocalAuthenticatorByName(config.getName())); + } + + @Test(priority = 51, expectedExceptions = AuthenticatorMgtException.class, + expectedExceptionsMessageRegExp = "No Authenticator found.") + public void testDeleteUserDefinedLocalAuthenticatorWithNonExistingAuthenticator() throws AuthenticatorMgtException { + + ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() + .deleteUserDefinedLocalAuthenticator(nonExistAuthenticatorConfig.getName(), tenantDomain); + } + + private UserDefinedLocalAuthenticatorConfig createUserDefinedAuthenticatorConfig(String uniqueIdentifier, + AuthenticationType type) { + + UserDefinedLocalAuthenticatorConfig authenticatorConfig = new + UserDefinedLocalAuthenticatorConfig(AuthenticationType.IDENTIFICATION); + authenticatorConfig.setName(uniqueIdentifier); + authenticatorConfig.setDisplayName("Custom " + uniqueIdentifier); + authenticatorConfig.setEnabled(true); + authenticatorConfig.setDefinedByType(DefinedByType.USER); + authenticatorConfig.setAuthenticationType(type); + UserDefinedAuthenticatorEndpointConfigBuilder endpointConfigBuilder = buildAuthenticatorEndpointConfig(); + authenticatorConfig.setEndpointConfig(endpointConfigBuilder.build()); + + return authenticatorConfig; + } + + private LocalAuthenticatorConfig createSystemDefinedAuthenticatorConfig(String uniqueIdentifier) { + + LocalAuthenticatorConfig authenticatorConfig = new LocalAuthenticatorConfig(); + authenticatorConfig.setName(uniqueIdentifier); + authenticatorConfig.setDisplayName("Custom " + uniqueIdentifier); + authenticatorConfig.setEnabled(true); + authenticatorConfig.setDefinedByType(DefinedByType.SYSTEM); + Property prop1 = new Property(); + prop1.setName("PropertyName1_" + uniqueIdentifier); + prop1.setValue("PropertyValue1_" + uniqueIdentifier); + prop1.setConfidential(false); + Property prop2 = new Property(); + prop2.setName("PropertyName2_" + uniqueIdentifier); + prop2.setValue("PropertyValue2_" + uniqueIdentifier); + prop2.setConfidential(true); + authenticatorConfig.setProperties(new Property[]{prop1, prop2}); + + return authenticatorConfig; + } + + private static UserDefinedAuthenticatorEndpointConfigBuilder buildAuthenticatorEndpointConfig() { + + UserDefinedAuthenticatorEndpointConfigBuilder endpointConfigBuilder = + new UserDefinedAuthenticatorEndpointConfigBuilder(); + endpointConfigBuilder.uri("https://localhost:8080/test"); + endpointConfigBuilder.authenticationType(Authentication.Type.BASIC.getName()); + HashMap authProperties = new HashMap<>(); + authProperties.put("username", "admin"); + authProperties.put("password", "admin"); + endpointConfigBuilder.authenticationProperties(authProperties); + return endpointConfigBuilder; + } +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/util/ActionMgtTestUtil.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/util/ActionMgtTestUtil.java new file mode 100644 index 000000000000..108bfe4e0ce2 --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/util/ActionMgtTestUtil.java @@ -0,0 +1,96 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.model.test.util; + +import org.wso2.carbon.identity.action.management.model.Action; +import org.wso2.carbon.identity.action.management.model.Authentication; +import org.wso2.carbon.identity.action.management.model.EndpointConfig; +import org.wso2.carbon.identity.application.common.model.FederatedAuthenticatorConfig; +import org.wso2.carbon.identity.application.common.model.IdentityProvider; +import org.wso2.carbon.identity.application.common.model.Property; +import org.wso2.carbon.identity.application.common.model.UserDefinedAuthenticatorEndpointConfig; +import org.wso2.carbon.identity.application.common.model.UserDefinedFederatedAuthenticatorConfig; + +import java.util.HashMap; +import java.util.Map; + +public class ActionMgtTestUtil { + + public static final String ASSOCIATED_ACTION_ID = "Dummy_Action_ID"; + + public static Action createAction(EndpointConfig endpointConfig) { + + Action.ActionResponseBuilder actionResponseBuilder = new Action.ActionResponseBuilder(); + actionResponseBuilder.id(ASSOCIATED_ACTION_ID); + actionResponseBuilder.name("SampleAssociatedAction"); + actionResponseBuilder.type(Action.ActionTypes.AUTHENTICATION); + actionResponseBuilder.description("SampleDescription"); + actionResponseBuilder.status(Action.Status.ACTIVE); + actionResponseBuilder.endpoint(endpointConfig); + return actionResponseBuilder.build(); + } + + public static EndpointConfig createEndpointConfig(String uri, String username, String password) { + + EndpointConfig.EndpointConfigBuilder endpointConfigBuilder = new EndpointConfig.EndpointConfigBuilder(); + endpointConfigBuilder.uri(uri); + endpointConfigBuilder.authentication( + new Authentication.BasicAuthBuilder(username, password).build()); + return endpointConfigBuilder.build(); + } + + public static IdentityProvider createIdPWithUserDefinedFederatedAuthenticatorConfig(String idpName, + EndpointConfig endpointConfig) { + + // Initialize Test Identity Provider 4 with custom user defined federated authenticator. + IdentityProvider newUserDefinedIdp = new IdentityProvider(); + newUserDefinedIdp.setIdentityProviderName(idpName); + + UserDefinedFederatedAuthenticatorConfig userDefinedFederatedAuthenticatorConfig = new + UserDefinedFederatedAuthenticatorConfig(); + userDefinedFederatedAuthenticatorConfig.setDisplayName("DisplayName1"); + userDefinedFederatedAuthenticatorConfig.setName("customFedAuthenticator"); + userDefinedFederatedAuthenticatorConfig.setEnabled(true); + userDefinedFederatedAuthenticatorConfig.setEndpointConfig( + buildUserDefinedAuthenticatorEndpointConfig(endpointConfig)); + Property property = new Property(); + property.setName("actionId"); + property.setValue(ASSOCIATED_ACTION_ID); + property.setConfidential(false); + userDefinedFederatedAuthenticatorConfig.setProperties(new Property[]{property}); + newUserDefinedIdp.setFederatedAuthenticatorConfigs( + new FederatedAuthenticatorConfig[]{userDefinedFederatedAuthenticatorConfig}); + newUserDefinedIdp.setDefaultAuthenticatorConfig(userDefinedFederatedAuthenticatorConfig); + return newUserDefinedIdp; + } + + public static UserDefinedAuthenticatorEndpointConfig buildUserDefinedAuthenticatorEndpointConfig( + EndpointConfig endpointConfig) { + + UserDefinedAuthenticatorEndpointConfig.UserDefinedAuthenticatorEndpointConfigBuilder endpointConfigBuilder = + new UserDefinedAuthenticatorEndpointConfig.UserDefinedAuthenticatorEndpointConfigBuilder(); + endpointConfigBuilder.uri(endpointConfig.getUri()); + endpointConfigBuilder.authenticationType(endpointConfig.getAuthentication().getType().getName()); + Map propMap = new HashMap<>(); + endpointConfig.getAuthentication().getProperties() + .forEach(prop -> propMap.put(prop.getName(), prop.getValue())); + endpointConfigBuilder.authenticationProperties(propMap); + return endpointConfigBuilder.build(); + } +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/dbscripts/h2.sql b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/dbscripts/h2.sql new file mode 100644 index 000000000000..2460775fdce3 --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/dbscripts/h2.sql @@ -0,0 +1,1482 @@ +CREATE TABLE IF NOT EXISTS IDN_BASE_TABLE ( + PRODUCT_NAME VARCHAR (20), + PRIMARY KEY (PRODUCT_NAME) +); + +INSERT INTO IDN_BASE_TABLE values ('WSO2 Identity Server'); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH_CONSUMER_APPS ( + ID INTEGER NOT NULL AUTO_INCREMENT, + CONSUMER_KEY VARCHAR (255), + CONSUMER_SECRET VARCHAR (2048), + USERNAME VARCHAR (255), + TENANT_ID INTEGER DEFAULT 0, + USER_DOMAIN VARCHAR(50), + APP_NAME VARCHAR (255), + OAUTH_VERSION VARCHAR (128), + CALLBACK_URL VARCHAR (2048), + GRANT_TYPES VARCHAR (1024), + PKCE_MANDATORY CHAR(1) DEFAULT '0', + PKCE_SUPPORT_PLAIN CHAR(1) DEFAULT '0', + APP_STATE VARCHAR (25) DEFAULT 'ACTIVE', + USER_ACCESS_TOKEN_EXPIRE_TIME BIGINT DEFAULT 3600, + APP_ACCESS_TOKEN_EXPIRE_TIME BIGINT DEFAULT 3600, + REFRESH_TOKEN_EXPIRE_TIME BIGINT DEFAULT 84600, + ID_TOKEN_EXPIRE_TIME BIGINT DEFAULT 3600, + CONSTRAINT CONSUMER_KEY_CONSTRAINT UNIQUE (TENANT_ID, CONSUMER_KEY), + PRIMARY KEY (ID) +); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH2_SCOPE_VALIDATORS ( + APP_ID INTEGER NOT NULL, + SCOPE_VALIDATOR VARCHAR (128) NOT NULL, + PRIMARY KEY (APP_ID,SCOPE_VALIDATOR), + FOREIGN KEY (APP_ID) REFERENCES IDN_OAUTH_CONSUMER_APPS(ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH1A_REQUEST_TOKEN ( + REQUEST_TOKEN VARCHAR (512), + REQUEST_TOKEN_SECRET VARCHAR (512), + CONSUMER_KEY_ID INTEGER, + CALLBACK_URL VARCHAR (2048), + SCOPE VARCHAR(2048), + AUTHORIZED VARCHAR (128), + OAUTH_VERIFIER VARCHAR (512), + AUTHZ_USER VARCHAR (512), + TENANT_ID INTEGER DEFAULT -1, + PRIMARY KEY (REQUEST_TOKEN), + FOREIGN KEY (CONSUMER_KEY_ID) REFERENCES IDN_OAUTH_CONSUMER_APPS(ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH1A_ACCESS_TOKEN ( + ACCESS_TOKEN VARCHAR (512), + ACCESS_TOKEN_SECRET VARCHAR (512), + CONSUMER_KEY_ID INTEGER, + SCOPE VARCHAR(2048), + AUTHZ_USER VARCHAR (512), + TENANT_ID INTEGER DEFAULT -1, + PRIMARY KEY (ACCESS_TOKEN), + FOREIGN KEY (CONSUMER_KEY_ID) REFERENCES IDN_OAUTH_CONSUMER_APPS(ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH2_ACCESS_TOKEN ( + TOKEN_ID VARCHAR (255), + ACCESS_TOKEN VARCHAR (2048), + REFRESH_TOKEN VARCHAR (2048), + CONSUMER_KEY_ID INTEGER, + AUTHZ_USER VARCHAR (100), + TENANT_ID INTEGER, + USER_DOMAIN VARCHAR(50), + USER_TYPE VARCHAR (25), + GRANT_TYPE VARCHAR (50), + TIME_CREATED TIMESTAMP DEFAULT 0, + REFRESH_TOKEN_TIME_CREATED TIMESTAMP DEFAULT 0, + VALIDITY_PERIOD BIGINT, + REFRESH_TOKEN_VALIDITY_PERIOD BIGINT, + TOKEN_SCOPE_HASH VARCHAR (32), + TOKEN_STATE VARCHAR (25) DEFAULT 'ACTIVE', + TOKEN_STATE_ID VARCHAR (128) DEFAULT 'NONE', + SUBJECT_IDENTIFIER VARCHAR(255), + ACCESS_TOKEN_HASH VARCHAR (512), + REFRESH_TOKEN_HASH VARCHAR (512), + IDP_ID INTEGER DEFAULT -1 NOT NULL, + TOKEN_BINDING_REF VARCHAR (32) DEFAULT 'NONE', + CONSENTED_TOKEN VARCHAR(6), + AUTHORIZED_ORGANIZATION VARCHAR(36) DEFAULT 'NONE' NOT NULL, + PRIMARY KEY (TOKEN_ID), + FOREIGN KEY (CONSUMER_KEY_ID) REFERENCES IDN_OAUTH_CONSUMER_APPS(ID) ON DELETE CASCADE, + CONSTRAINT CON_APP_KEY UNIQUE (CONSUMER_KEY_ID,AUTHZ_USER,TENANT_ID,USER_DOMAIN,USER_TYPE,TOKEN_SCOPE_HASH, + TOKEN_STATE,TOKEN_STATE_ID,IDP_ID,TOKEN_BINDING_REF,AUTHORIZED_ORGANIZATION) +); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH2_TOKEN_BINDING ( + TOKEN_ID VARCHAR (255), + TOKEN_BINDING_TYPE VARCHAR (32), + TOKEN_BINDING_REF VARCHAR (32), + TOKEN_BINDING_VALUE VARCHAR (1024), + TENANT_ID INTEGER DEFAULT -1, + UNIQUE (TOKEN_ID,TOKEN_BINDING_TYPE,TOKEN_BINDING_VALUE), + FOREIGN KEY (TOKEN_ID) REFERENCES IDN_OAUTH2_ACCESS_TOKEN(TOKEN_ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH2_ACCESS_TOKEN_AUDIT ( + ID INTEGER NOT NULL AUTO_INCREMENT, + TOKEN_ID VARCHAR (255), + ACCESS_TOKEN VARCHAR(2048), + REFRESH_TOKEN VARCHAR(2048), + CONSUMER_KEY_ID INTEGER, + AUTHZ_USER VARCHAR (100), + TENANT_ID INTEGER, + USER_DOMAIN VARCHAR(50), + USER_TYPE VARCHAR (25), + GRANT_TYPE VARCHAR (50), + TIME_CREATED TIMESTAMP NULL, + REFRESH_TOKEN_TIME_CREATED TIMESTAMP NULL, + VALIDITY_PERIOD BIGINT, + REFRESH_TOKEN_VALIDITY_PERIOD BIGINT, + TOKEN_SCOPE_HASH VARCHAR(32), + TOKEN_STATE VARCHAR(25), + TOKEN_STATE_ID VARCHAR (128) , + SUBJECT_IDENTIFIER VARCHAR(255), + ACCESS_TOKEN_HASH VARCHAR(512), + REFRESH_TOKEN_HASH VARCHAR(512), + INVALIDATED_TIME TIMESTAMP NULL, + IDP_ID INTEGER DEFAULT -1 NOT NULL, + PRIMARY KEY(ID) +); + + +CREATE TABLE IF NOT EXISTS IDN_OAUTH2_AUTHORIZATION_CODE ( + CODE_ID VARCHAR (255), + AUTHORIZATION_CODE VARCHAR (2048), + CONSUMER_KEY_ID INTEGER, + CALLBACK_URL VARCHAR (2048), + SCOPE VARCHAR(2048), + AUTHZ_USER VARCHAR (100), + TENANT_ID INTEGER, + USER_DOMAIN VARCHAR(50), + TIME_CREATED TIMESTAMP, + VALIDITY_PERIOD BIGINT, + STATE VARCHAR (25) DEFAULT 'ACTIVE', + TOKEN_ID VARCHAR(255), + SUBJECT_IDENTIFIER VARCHAR(255), + PKCE_CODE_CHALLENGE VARCHAR (255), + PKCE_CODE_CHALLENGE_METHOD VARCHAR(128), + AUTHORIZATION_CODE_HASH VARCHAR (512), + IDP_ID INTEGER DEFAULT -1 NOT NULL, + PRIMARY KEY (CODE_ID), + FOREIGN KEY (CONSUMER_KEY_ID) REFERENCES IDN_OAUTH_CONSUMER_APPS(ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH2_AUTHZ_CODE_SCOPE( + CODE_ID VARCHAR(255), + SCOPE VARCHAR(255), + TENANT_ID INTEGER DEFAULT -1, + PRIMARY KEY (CODE_ID, SCOPE), + FOREIGN KEY (CODE_ID) REFERENCES IDN_OAUTH2_AUTHORIZATION_CODE (CODE_ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH2_DEVICE_FLOW ( + CODE_ID VARCHAR(255), + DEVICE_CODE VARCHAR(255), + USER_CODE VARCHAR(25), + QUANTIFIER INTEGER NOT NULL DEFAULT 0, + CONSUMER_KEY_ID INTEGER, + LAST_POLL_TIME TIMESTAMP NOT NULL, + EXPIRY_TIME TIMESTAMP NOT NULL, + TIME_CREATED TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, + POLL_TIME BIGINT, + STATUS VARCHAR (25) DEFAULT 'PENDING', + AUTHZ_USER VARCHAR (100), + TENANT_ID INTEGER, + USER_DOMAIN VARCHAR(50), + IDP_ID INTEGER, + SUBJECT_IDENTIFIER VARCHAR(255), + PRIMARY KEY (DEVICE_CODE), + UNIQUE (CODE_ID), + CONSTRAINT USRCDE_QNTFR_CONSTRAINT UNIQUE (USER_CODE, QUANTIFIER), + FOREIGN KEY (CONSUMER_KEY_ID) REFERENCES IDN_OAUTH_CONSUMER_APPS(ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH2_DEVICE_FLOW_SCOPES ( + ID INTEGER NOT NULL AUTO_INCREMENT, + SCOPE_ID VARCHAR(255), + SCOPE VARCHAR(255), + PRIMARY KEY (ID), + FOREIGN KEY (SCOPE_ID) REFERENCES IDN_OAUTH2_DEVICE_FLOW(CODE_ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH2_ACCESS_TOKEN_SCOPE ( + TOKEN_ID VARCHAR (255), + TOKEN_SCOPE VARCHAR (255), + TENANT_ID INTEGER DEFAULT -1, + PRIMARY KEY (TOKEN_ID, TOKEN_SCOPE), + FOREIGN KEY (TOKEN_ID) REFERENCES IDN_OAUTH2_ACCESS_TOKEN(TOKEN_ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH2_SCOPE ( + SCOPE_ID INTEGER NOT NULL AUTO_INCREMENT, + NAME VARCHAR(255) NOT NULL, + DISPLAY_NAME VARCHAR(255) NOT NULL, + DESCRIPTION VARCHAR(512), + TENANT_ID INTEGER NOT NULL DEFAULT -1, + SCOPE_TYPE VARCHAR(255) NOT NULL, + PRIMARY KEY (SCOPE_ID), + UNIQUE (NAME, TENANT_ID) +); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH2_SCOPE_BINDING ( + ID INTEGER NOT NULL AUTO_INCREMENT, + SCOPE_ID INTEGER NOT NULL, + SCOPE_BINDING VARCHAR(255) NOT NULL, + BINDING_TYPE VARCHAR(255) NOT NULL, + FOREIGN KEY (SCOPE_ID) REFERENCES IDN_OAUTH2_SCOPE(SCOPE_ID) ON DELETE CASCADE, + UNIQUE (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE), + PRIMARY KEY (ID) +); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH2_RESOURCE_SCOPE ( + RESOURCE_PATH VARCHAR(255) NOT NULL, + SCOPE_ID INTEGER NOT NULL, + TENANT_ID INTEGER DEFAULT -1, + PRIMARY KEY (RESOURCE_PATH), + FOREIGN KEY (SCOPE_ID) REFERENCES IDN_OAUTH2_SCOPE (SCOPE_ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDN_SCIM_GROUP ( + ID INTEGER NOT NULL AUTO_INCREMENT, + TENANT_ID INTEGER NOT NULL, + ROLE_NAME VARCHAR(255) NOT NULL, + ATTR_NAME VARCHAR(1024) NOT NULL, + ATTR_VALUE VARCHAR(1024), + AUDIENCE_REF_ID INTEGER DEFAULT -1 NOT NULL, + UNIQUE(TENANT_ID, ROLE_NAME, ATTR_NAME, AUDIENCE_REF_ID), + PRIMARY KEY (ID) +); + + + +CREATE TABLE IF NOT EXISTS IDN_OPENID_REMEMBER_ME ( + USER_NAME VARCHAR(255) NOT NULL, + TENANT_ID INTEGER DEFAULT 0, + COOKIE_VALUE VARCHAR(1024), + CREATED_TIME TIMESTAMP, + PRIMARY KEY (USER_NAME, TENANT_ID) +); + +CREATE TABLE IF NOT EXISTS IDN_OPENID_USER_RPS ( + USER_NAME VARCHAR(255) NOT NULL, + TENANT_ID INTEGER DEFAULT 0, + RP_URL VARCHAR(255) NOT NULL, + TRUSTED_ALWAYS VARCHAR(128) DEFAULT 'FALSE', + LAST_VISIT DATE NOT NULL, + VISIT_COUNT INTEGER DEFAULT 0, + DEFAULT_PROFILE_NAME VARCHAR(255) DEFAULT 'DEFAULT', + PRIMARY KEY (USER_NAME, TENANT_ID, RP_URL) +); + +CREATE TABLE IF NOT EXISTS IDN_OPENID_ASSOCIATIONS ( + HANDLE VARCHAR(255) NOT NULL, + ASSOC_TYPE VARCHAR(255) NOT NULL, + EXPIRE_IN TIMESTAMP NOT NULL, + MAC_KEY VARCHAR(255) NOT NULL, + ASSOC_STORE VARCHAR(128) DEFAULT 'SHARED', + TENANT_ID INTEGER DEFAULT -1, + PRIMARY KEY (HANDLE) +); + +CREATE TABLE IDN_STS_STORE ( + ID INTEGER AUTO_INCREMENT, + TOKEN_ID VARCHAR(255) NOT NULL, + TOKEN_CONTENT BLOB(1024) NOT NULL, + CREATE_DATE TIMESTAMP NOT NULL, + EXPIRE_DATE TIMESTAMP NOT NULL, + STATE INTEGER DEFAULT 0, + PRIMARY KEY (ID) +); + +CREATE TABLE IDN_IDENTITY_USER_DATA ( + TENANT_ID INTEGER DEFAULT -1234, + USER_NAME VARCHAR(255) NOT NULL, + DATA_KEY VARCHAR(255) NOT NULL, + DATA_VALUE VARCHAR(2048), + PRIMARY KEY (TENANT_ID, USER_NAME, DATA_KEY) +); + +CREATE TABLE IDN_IDENTITY_META_DATA ( + USER_NAME VARCHAR(255) NOT NULL, + TENANT_ID INTEGER DEFAULT -1234, + METADATA_TYPE VARCHAR(255) NOT NULL, + METADATA VARCHAR(255) NOT NULL, + VALID VARCHAR(255) NOT NULL, + PRIMARY KEY (TENANT_ID, USER_NAME, METADATA_TYPE,METADATA) +); + +CREATE TABLE IF NOT EXISTS IDN_THRIFT_SESSION ( + SESSION_ID VARCHAR(255) NOT NULL, + USER_NAME VARCHAR(255) NOT NULL, + CREATED_TIME VARCHAR(255) NOT NULL, + LAST_MODIFIED_TIME VARCHAR(255) NOT NULL, + TENANT_ID INTEGER DEFAULT -1, + PRIMARY KEY (SESSION_ID) +); + +CREATE TABLE IDN_AUTH_SESSION_STORE ( + SESSION_ID VARCHAR (100) NOT NULL, + SESSION_TYPE VARCHAR(100) NOT NULL, + OPERATION VARCHAR(10) NOT NULL, + SESSION_OBJECT BLOB, + TIME_CREATED BIGINT, + TENANT_ID INTEGER DEFAULT -1, + EXPIRY_TIME BIGINT, + PRIMARY KEY (SESSION_ID, SESSION_TYPE, TIME_CREATED, OPERATION) +); + + +CREATE TABLE IDN_AUTH_TEMP_SESSION_STORE ( + SESSION_ID VARCHAR (100) NOT NULL, + SESSION_TYPE VARCHAR(100) NOT NULL, + OPERATION VARCHAR(10) NOT NULL, + SESSION_OBJECT BLOB, + TIME_CREATED BIGINT, + TENANT_ID INTEGER DEFAULT -1, + EXPIRY_TIME BIGINT, + PRIMARY KEY (SESSION_ID, SESSION_TYPE, TIME_CREATED, OPERATION) +); + +CREATE TABLE IF NOT EXISTS IDN_AUTH_USER ( + USER_ID VARCHAR(255) NOT NULL, + USER_NAME VARCHAR(255) NOT NULL, + TENANT_ID INTEGER NOT NULL, + DOMAIN_NAME VARCHAR(255) NOT NULL, + IDP_ID INTEGER NOT NULL, + PRIMARY KEY (USER_ID), + CONSTRAINT USER_STORE_CONSTRAINT UNIQUE (USER_NAME, TENANT_ID, DOMAIN_NAME, IDP_ID)); + +CREATE TABLE IF NOT EXISTS IDN_AUTH_USER_SESSION_MAPPING ( + ID INTEGER NOT NULL AUTO_INCREMENT, + USER_ID VARCHAR(255) NOT NULL, + SESSION_ID VARCHAR(255) NOT NULL, + CONSTRAINT USER_SESSION_STORE_CONSTRAINT UNIQUE (USER_ID, SESSION_ID), + PRIMARY KEY (ID)); + +CREATE TABLE IF NOT EXISTS IDN_AUTH_SESSION_APP_INFO ( + SESSION_ID VARCHAR (100) NOT NULL, + SUBJECT VARCHAR (100) NOT NULL, + APP_ID INTEGER NOT NULL, + INBOUND_AUTH_TYPE VARCHAR (255) NOT NULL, + PRIMARY KEY (SESSION_ID, SUBJECT, APP_ID, INBOUND_AUTH_TYPE)); + +CREATE TABLE IF NOT EXISTS IDN_AUTH_SESSION_META_DATA ( + SESSION_ID VARCHAR (100) NOT NULL, + PROPERTY_TYPE VARCHAR (100) NOT NULL, + `VALUE` VARCHAR (255) NOT NULL, + PRIMARY KEY (SESSION_ID, PROPERTY_TYPE, `VALUE`) + ); + +CREATE TABLE IF NOT EXISTS SP_APP ( + ID INTEGER NOT NULL AUTO_INCREMENT, + TENANT_ID INTEGER NOT NULL, + APP_NAME VARCHAR (255) NOT NULL , + USER_STORE VARCHAR (255) NOT NULL, + USERNAME VARCHAR (255) NOT NULL , + DESCRIPTION VARCHAR (1024), + ROLE_CLAIM VARCHAR (512), + AUTH_TYPE VARCHAR (255) NOT NULL, + PROVISIONING_USERSTORE_DOMAIN VARCHAR (512), + IS_LOCAL_CLAIM_DIALECT CHAR(1) DEFAULT '1', + IS_SEND_LOCAL_SUBJECT_ID CHAR(1) DEFAULT '0', + IS_SEND_AUTH_LIST_OF_IDPS CHAR(1) DEFAULT '0', + IS_USE_TENANT_DOMAIN_SUBJECT CHAR(1) DEFAULT '1', + IS_USE_USER_DOMAIN_SUBJECT CHAR(1) DEFAULT '1', + ENABLE_AUTHORIZATION CHAR(1) DEFAULT '0', + SUBJECT_CLAIM_URI VARCHAR (512), + IS_SAAS_APP CHAR(1) DEFAULT '0', + IS_DUMB_MODE CHAR(1) DEFAULT '0', + UUID CHAR(36), + IMAGE_URL VARCHAR(1024), + ACCESS_URL VARCHAR(1024), + IS_DISCOVERABLE CHAR(1) DEFAULT '0', + + PRIMARY KEY (ID)); + +ALTER TABLE SP_APP ADD CONSTRAINT APPLICATION_NAME_CONSTRAINT UNIQUE(APP_NAME, TENANT_ID); +ALTER TABLE SP_APP ADD CONSTRAINT APPLICATION_UUID_CONSTRAINT UNIQUE(UUID); + +CREATE TABLE IF NOT EXISTS SP_METADATA ( + ID INTEGER AUTO_INCREMENT, + SP_ID INTEGER, + NAME VARCHAR(255) NOT NULL, + `VALUE` VARCHAR(255) NOT NULL, + DISPLAY_NAME VARCHAR(255), + TENANT_ID INTEGER DEFAULT -1, + PRIMARY KEY (ID), + CONSTRAINT SP_METADATA_CONSTRAINT UNIQUE (SP_ID, NAME), + FOREIGN KEY (SP_ID) REFERENCES SP_APP(ID) ON DELETE CASCADE); + +CREATE TABLE IF NOT EXISTS SP_INBOUND_AUTH ( + ID INTEGER NOT NULL AUTO_INCREMENT, + TENANT_ID INTEGER NOT NULL, + INBOUND_AUTH_KEY VARCHAR (255), + INBOUND_AUTH_TYPE VARCHAR (255) NOT NULL, + INBOUND_CONFIG_TYPE VARCHAR (255) NOT NULL, + PROP_NAME VARCHAR (255), + PROP_VALUE VARCHAR (1024) , + APP_ID INTEGER NOT NULL, + PRIMARY KEY (ID)); + +ALTER TABLE SP_INBOUND_AUTH ADD CONSTRAINT APPLICATION_ID_CONSTRAINT FOREIGN KEY (APP_ID) REFERENCES SP_APP (ID) ON DELETE CASCADE; + +CREATE TABLE IF NOT EXISTS SP_AUTH_STEP ( + ID INTEGER NOT NULL AUTO_INCREMENT, + TENANT_ID INTEGER NOT NULL, + STEP_ORDER INTEGER DEFAULT 1, + APP_ID INTEGER NOT NULL , + IS_SUBJECT_STEP CHAR(1) DEFAULT '0', + IS_ATTRIBUTE_STEP CHAR(1) DEFAULT '0', + PRIMARY KEY (ID)); + +ALTER TABLE SP_AUTH_STEP ADD CONSTRAINT APPLICATION_ID_CONSTRAINT_STEP FOREIGN KEY (APP_ID) REFERENCES SP_APP (ID) ON DELETE CASCADE; + +CREATE TABLE IF NOT EXISTS SP_FEDERATED_IDP ( + ID INTEGER NOT NULL, + TENANT_ID INTEGER NOT NULL, + AUTHENTICATOR_ID INTEGER NOT NULL, + PRIMARY KEY (ID, AUTHENTICATOR_ID)); + +ALTER TABLE SP_FEDERATED_IDP ADD CONSTRAINT STEP_ID_CONSTRAINT FOREIGN KEY (ID) REFERENCES SP_AUTH_STEP (ID) ON DELETE CASCADE; + +CREATE TABLE IF NOT EXISTS SP_CLAIM_DIALECT ( + ID INTEGER NOT NULL AUTO_INCREMENT, + TENANT_ID INTEGER NOT NULL, + SP_DIALECT VARCHAR (512) NOT NULL, + APP_ID INTEGER NOT NULL, + PRIMARY KEY (ID)); + +ALTER TABLE SP_CLAIM_DIALECT ADD CONSTRAINT DIALECTID_APPID_CONSTRAINT FOREIGN KEY (APP_ID) REFERENCES SP_APP (ID) ON DELETE CASCADE; + +CREATE TABLE IF NOT EXISTS SP_CLAIM_MAPPING ( + ID INTEGER NOT NULL AUTO_INCREMENT, + TENANT_ID INTEGER NOT NULL, + IDP_CLAIM VARCHAR (512) NOT NULL , + SP_CLAIM VARCHAR (512) NOT NULL , + APP_ID INTEGER NOT NULL, + IS_REQUESTED VARCHAR(128) DEFAULT '0', + IS_MANDATORY VARCHAR(128) DEFAULT '0', + DEFAULT_VALUE VARCHAR(255), + PRIMARY KEY (ID)); + +ALTER TABLE SP_CLAIM_MAPPING ADD CONSTRAINT CLAIMID_APPID_CONSTRAINT FOREIGN KEY (APP_ID) REFERENCES SP_APP (ID) ON DELETE CASCADE; + +CREATE TABLE IF NOT EXISTS SP_ROLE_MAPPING ( + ID INTEGER NOT NULL AUTO_INCREMENT, + TENANT_ID INTEGER NOT NULL, + IDP_ROLE VARCHAR (255) NOT NULL , + SP_ROLE VARCHAR (255) NOT NULL , + APP_ID INTEGER NOT NULL, + PRIMARY KEY (ID)); + +ALTER TABLE SP_ROLE_MAPPING ADD CONSTRAINT ROLEID_APPID_CONSTRAINT FOREIGN KEY (APP_ID) REFERENCES SP_APP (ID) ON DELETE CASCADE; + +CREATE TABLE IF NOT EXISTS SP_REQ_PATH_AUTHENTICATOR ( + ID INTEGER NOT NULL AUTO_INCREMENT, + TENANT_ID INTEGER NOT NULL, + AUTHENTICATOR_NAME VARCHAR (255) NOT NULL , + APP_ID INTEGER NOT NULL, + PRIMARY KEY (ID)); + +ALTER TABLE SP_REQ_PATH_AUTHENTICATOR ADD CONSTRAINT REQ_AUTH_APPID_CONSTRAINT FOREIGN KEY (APP_ID) REFERENCES SP_APP (ID) ON DELETE CASCADE; + +CREATE TABLE IF NOT EXISTS SP_PROVISIONING_CONNECTOR ( + ID INTEGER NOT NULL AUTO_INCREMENT, + TENANT_ID INTEGER NOT NULL, + IDP_NAME VARCHAR (255) NOT NULL , + CONNECTOR_NAME VARCHAR (255) NOT NULL , + APP_ID INTEGER NOT NULL, + IS_JIT_ENABLED CHAR(1) NOT NULL DEFAULT '0', + BLOCKING CHAR(1) NOT NULL DEFAULT '0', + RULE_ENABLED CHAR(1) NOT NULL DEFAULT '0', + PRIMARY KEY (ID)); + +ALTER TABLE SP_PROVISIONING_CONNECTOR ADD CONSTRAINT PRO_CONNECTOR_APPID_CONSTRAINT FOREIGN KEY (APP_ID) REFERENCES SP_APP (ID) ON DELETE CASCADE; + +CREATE TABLE IF NOT EXISTS SP_AUTH_SCRIPT ( + ID INTEGER AUTO_INCREMENT NOT NULL, + TENANT_ID INTEGER NOT NULL, + APP_ID INTEGER NOT NULL, + TYPE VARCHAR(255) NOT NULL, + CONTENT BLOB DEFAULT NULL, + IS_ENABLED CHAR(1) NOT NULL DEFAULT '0', + PRIMARY KEY (ID)); + +CREATE TABLE SP_TEMPLATE ( + ID INTEGER AUTO_INCREMENT NOT NULL, + TENANT_ID INTEGER NOT NULL, + NAME VARCHAR(255) NOT NULL, + DESCRIPTION VARCHAR(1023), + CONTENT BLOB DEFAULT NULL, + PRIMARY KEY (ID), + CONSTRAINT SP_TEMPLATE_CONSTRAINT UNIQUE (TENANT_ID, NAME)); + +CREATE TABLE IF NOT EXISTS SP_TRUSTED_APPS ( + ID INTEGER AUTO_INCREMENT, + SP_ID INTEGER NOT NULL, + PLATFORM_TYPE VARCHAR(255) NOT NULL, + APP_IDENTIFIER VARCHAR(255) NOT NULL, + THUMBPRINTS VARCHAR(2048), + IS_FIDO_TRUSTED BOOLEAN DEFAULT FALSE, + TENANT_ID INTEGER NOT NULL, + PRIMARY KEY (ID), + UNIQUE (SP_ID, PLATFORM_TYPE), + FOREIGN KEY (SP_ID) REFERENCES SP_APP(ID) ON DELETE CASCADE); + +CREATE TABLE IF NOT EXISTS IDN_AUTH_WAIT_STATUS ( + ID INTEGER AUTO_INCREMENT NOT NULL, + TENANT_ID INTEGER NOT NULL, + LONG_WAIT_KEY VARCHAR(255) NOT NULL, + WAIT_STATUS CHAR(1) NOT NULL DEFAULT '1', + TIME_CREATED TIMESTAMP DEFAULT 0, + EXPIRE_TIME TIMESTAMP DEFAULT 0, + PRIMARY KEY (ID), + CONSTRAINT IDN_AUTH_WAIT_STATUS_KEY UNIQUE (LONG_WAIT_KEY)); + +CREATE TABLE IF NOT EXISTS IDP ( + ID INTEGER AUTO_INCREMENT, + TENANT_ID INTEGER, + NAME VARCHAR(254) NOT NULL, + IS_ENABLED CHAR(1) NOT NULL DEFAULT '1', + IS_PRIMARY CHAR(1) NOT NULL DEFAULT '0', + HOME_REALM_ID VARCHAR(254), + IMAGE MEDIUMBLOB, + CERTIFICATE BLOB, + ALIAS VARCHAR(254), + INBOUND_PROV_ENABLED CHAR(1) NOT NULL DEFAULT '0', + INBOUND_PROV_USER_STORE_ID VARCHAR(254), + USER_CLAIM_URI VARCHAR(254), + ROLE_CLAIM_URI VARCHAR(254), + DESCRIPTION VARCHAR(1024), + DEFAULT_AUTHENTICATOR_NAME VARCHAR(254), + DEFAULT_PRO_CONNECTOR_NAME VARCHAR(254), + PROVISIONING_ROLE VARCHAR(128), + IS_FEDERATION_HUB CHAR(1) NOT NULL DEFAULT '0', + IS_LOCAL_CLAIM_DIALECT CHAR(1) NOT NULL DEFAULT '0', + DISPLAY_NAME VARCHAR(255), + IMAGE_URL VARCHAR(1024), + UUID CHAR(36) NOT NULL, + PRIMARY KEY (ID), + UNIQUE (TENANT_ID, NAME), + UNIQUE (UUID) +); + +CREATE TABLE IF NOT EXISTS IDP_ROLE ( + ID INTEGER AUTO_INCREMENT, + IDP_ID INTEGER, + TENANT_ID INTEGER, + ROLE VARCHAR(254), + PRIMARY KEY (ID), + UNIQUE (IDP_ID, ROLE), + FOREIGN KEY (IDP_ID) REFERENCES IDP(ID) ON DELETE CASCADE); + +CREATE TABLE IF NOT EXISTS IDP_GROUP ( + ID INTEGER AUTO_INCREMENT NOT NULL, + IDP_ID INTEGER NOT NULL, + TENANT_ID INTEGER NOT NULL, + GROUP_NAME VARCHAR(255) NOT NULL, + UUID CHAR(36) NOT NULL, + PRIMARY KEY (ID), + UNIQUE (IDP_ID, GROUP_NAME), + UNIQUE (UUID), + FOREIGN KEY (IDP_ID) REFERENCES IDP(ID) ON DELETE CASCADE); + +CREATE TABLE IF NOT EXISTS IDP_ROLE_MAPPING ( + ID INTEGER AUTO_INCREMENT, + IDP_ROLE_ID INTEGER, + TENANT_ID INTEGER, + USER_STORE_ID VARCHAR (253), + LOCAL_ROLE VARCHAR(253), + PRIMARY KEY (ID), + UNIQUE (IDP_ROLE_ID, TENANT_ID, USER_STORE_ID, LOCAL_ROLE), + FOREIGN KEY (IDP_ROLE_ID) REFERENCES IDP_ROLE(ID) ON DELETE CASCADE); + +CREATE TABLE IF NOT EXISTS IDP_CLAIM ( + ID INTEGER AUTO_INCREMENT, + IDP_ID INTEGER, + TENANT_ID INTEGER, + CLAIM VARCHAR(254), + PRIMARY KEY (ID), + UNIQUE (IDP_ID, CLAIM), + FOREIGN KEY (IDP_ID) REFERENCES IDP(ID) ON DELETE CASCADE); + +CREATE TABLE IF NOT EXISTS IDP_CLAIM_MAPPING ( + ID INTEGER AUTO_INCREMENT, + IDP_CLAIM_ID INTEGER, + TENANT_ID INTEGER, + LOCAL_CLAIM VARCHAR(253), + DEFAULT_VALUE VARCHAR(255), + IS_REQUESTED VARCHAR(128) DEFAULT '0', + PRIMARY KEY (ID), + UNIQUE (IDP_CLAIM_ID, TENANT_ID, LOCAL_CLAIM), + FOREIGN KEY (IDP_CLAIM_ID) REFERENCES IDP_CLAIM(ID) ON DELETE CASCADE); + +CREATE TABLE IF NOT EXISTS IDP_AUTHENTICATOR ( + ID INTEGER AUTO_INCREMENT, + TENANT_ID INTEGER, + IDP_ID INTEGER, + NAME VARCHAR(255) NOT NULL, + IS_ENABLED CHAR (1) DEFAULT '1', + DISPLAY_NAME VARCHAR(255), + DEFINED_BY VARCHAR(25) NOT NULL, + AUTHENTICATION_TYPE VARCHAR(25) NOT NULL, + PRIMARY KEY (ID), + UNIQUE (TENANT_ID, IDP_ID, NAME), + FOREIGN KEY (IDP_ID) REFERENCES IDP(ID) ON DELETE CASCADE); + +CREATE TABLE IF NOT EXISTS IDP_METADATA ( + ID INTEGER AUTO_INCREMENT, + IDP_ID INTEGER, + NAME VARCHAR(255) NOT NULL, + `VALUE` VARCHAR(255) NOT NULL, + DISPLAY_NAME VARCHAR(255), + TENANT_ID INTEGER DEFAULT -1, + PRIMARY KEY (ID), + CONSTRAINT IDP_METADATA_CONSTRAINT UNIQUE (IDP_ID, NAME), + FOREIGN KEY (IDP_ID) REFERENCES IDP(ID) ON DELETE CASCADE); + +CREATE TABLE IF NOT EXISTS IDP_AUTHENTICATOR_PROPERTY ( + ID INTEGER AUTO_INCREMENT, + TENANT_ID INTEGER, + AUTHENTICATOR_ID INTEGER, + PROPERTY_KEY VARCHAR(255) NOT NULL, + PROPERTY_VALUE VARCHAR(2047), + IS_SECRET CHAR (1) DEFAULT '0', + PRIMARY KEY (ID), + UNIQUE (TENANT_ID, AUTHENTICATOR_ID, PROPERTY_KEY), + FOREIGN KEY (AUTHENTICATOR_ID) REFERENCES IDP_AUTHENTICATOR(ID) ON DELETE CASCADE); + +CREATE TABLE IF NOT EXISTS IDP_PROVISIONING_CONFIG ( + ID INTEGER AUTO_INCREMENT, + TENANT_ID INTEGER, + IDP_ID INTEGER, + PROVISIONING_CONNECTOR_TYPE VARCHAR(255) NOT NULL, + IS_ENABLED CHAR (1) DEFAULT '0', + IS_BLOCKING CHAR (1) DEFAULT '0', + IS_RULES_ENABLED CHAR (1) DEFAULT '0', + PRIMARY KEY (ID), + UNIQUE (TENANT_ID, IDP_ID, PROVISIONING_CONNECTOR_TYPE), + FOREIGN KEY (IDP_ID) REFERENCES IDP(ID) ON DELETE CASCADE); + +CREATE TABLE IF NOT EXISTS IDP_PROV_CONFIG_PROPERTY ( + ID INTEGER AUTO_INCREMENT, + TENANT_ID INTEGER, + PROVISIONING_CONFIG_ID INTEGER, + PROPERTY_KEY VARCHAR(255) NOT NULL, + PROPERTY_VALUE VARCHAR(2048), + PROPERTY_BLOB_VALUE BLOB, + PROPERTY_TYPE VARCHAR(32) NOT NULL, + IS_SECRET CHAR (1) DEFAULT '0', + PRIMARY KEY (ID), + UNIQUE (TENANT_ID, PROVISIONING_CONFIG_ID, PROPERTY_KEY), + FOREIGN KEY (PROVISIONING_CONFIG_ID) REFERENCES IDP_PROVISIONING_CONFIG(ID) ON DELETE CASCADE); + +CREATE TABLE IF NOT EXISTS IDP_PROVISIONING_ENTITY ( + ID INTEGER AUTO_INCREMENT, + PROVISIONING_CONFIG_ID INTEGER, + ENTITY_TYPE VARCHAR(255) NOT NULL, + ENTITY_LOCAL_USERSTORE VARCHAR(255) NOT NULL, + ENTITY_NAME VARCHAR(255) NOT NULL, + ENTITY_VALUE VARCHAR(255), + TENANT_ID INTEGER, + ENTITY_LOCAL_ID VARCHAR(255), + PRIMARY KEY (ID), + UNIQUE (ENTITY_TYPE, TENANT_ID, ENTITY_LOCAL_USERSTORE, ENTITY_NAME, PROVISIONING_CONFIG_ID), + UNIQUE (PROVISIONING_CONFIG_ID, ENTITY_TYPE, ENTITY_VALUE), + FOREIGN KEY (PROVISIONING_CONFIG_ID) REFERENCES IDP_PROVISIONING_CONFIG(ID) ON DELETE CASCADE); + +CREATE TABLE IF NOT EXISTS IDP_LOCAL_CLAIM ( + ID INTEGER AUTO_INCREMENT, + TENANT_ID INTEGER, + IDP_ID INTEGER, + CLAIM_URI VARCHAR(255) NOT NULL, + DEFAULT_VALUE VARCHAR(255), + IS_REQUESTED VARCHAR(128) DEFAULT '0', + PRIMARY KEY (ID), + UNIQUE (TENANT_ID, IDP_ID, CLAIM_URI), + FOREIGN KEY (IDP_ID) REFERENCES IDP(ID) ON DELETE CASCADE); + +CREATE TABLE IF NOT EXISTS IDN_ASSOCIATED_ID ( + ID INTEGER AUTO_INCREMENT, + IDP_USER_ID VARCHAR(255) NOT NULL, + TENANT_ID INTEGER DEFAULT -1234, + IDP_ID INTEGER NOT NULL, + DOMAIN_NAME VARCHAR(255) NOT NULL, + USER_NAME VARCHAR(255) NOT NULL, + ASSOCIATION_ID CHAR(36) NOT NULL, + PRIMARY KEY (ID), + UNIQUE(IDP_USER_ID, TENANT_ID, IDP_ID), + FOREIGN KEY (IDP_ID) REFERENCES IDP(ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDN_USER_ACCOUNT_ASSOCIATION ( + ASSOCIATION_KEY VARCHAR(255) NOT NULL, + TENANT_ID INTEGER, + DOMAIN_NAME VARCHAR(255) NOT NULL, + USER_NAME VARCHAR(255) NOT NULL, + PRIMARY KEY (TENANT_ID, DOMAIN_NAME, USER_NAME)); + +CREATE TABLE IF NOT EXISTS FIDO_DEVICE_STORE ( + TENANT_ID INTEGER, + DOMAIN_NAME VARCHAR(255) NOT NULL, + USER_NAME VARCHAR(45) NOT NULL, + TIME_REGISTERED TIMESTAMP, + KEY_HANDLE VARCHAR(200) NOT NULL, + DEVICE_DATA VARCHAR(2048) NOT NULL, + PRIMARY KEY (TENANT_ID, DOMAIN_NAME, USER_NAME, KEY_HANDLE)); + +CREATE TABLE IF NOT EXISTS FIDO2_DEVICE_STORE ( + TENANT_ID INTEGER, + DOMAIN_NAME VARCHAR(255) NOT NULL, + USER_NAME VARCHAR(45) NOT NULL, + TIME_REGISTERED TIMESTAMP, + USER_HANDLE VARCHAR(200) NOT NULL, + CREDENTIAL_ID VARCHAR(200) NOT NULL, + PUBLIC_KEY_COSE VARCHAR(2048) NOT NULL, + SIGNATURE_COUNT BIGINT, + USER_IDENTITY VARCHAR(200) NOT NULL, + DISPLAY_NAME VARCHAR(255), + IS_USERNAMELESS_SUPPORTED CHAR(1) DEFAULT '0', + PRIMARY KEY (CREDENTIAL_ID, USER_HANDLE)); + +CREATE TABLE IF NOT EXISTS IDN_RECOVERY_FLOW_DATA ( + RECOVERY_FLOW_ID VARCHAR(255) NOT NULL, + CODE VARCHAR(255), + FAILED_ATTEMPTS INTEGER DEFAULT 0 NOT NULL, + RESEND_COUNT INTEGER DEFAULT 0 NOT NULL, + TIME_CREATED TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, + PRIMARY KEY(RECOVERY_FLOW_ID) +); + +CREATE TABLE IF NOT EXISTS IDN_RECOVERY_DATA ( + USER_NAME VARCHAR(255) NOT NULL, + USER_DOMAIN VARCHAR(127) NOT NULL, + TENANT_ID INTEGER DEFAULT -1, + CODE VARCHAR(255) NOT NULL, + SCENARIO VARCHAR(255) NOT NULL, + STEP VARCHAR(127) NOT NULL, + TIME_CREATED TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, + REMAINING_SETS VARCHAR(2500) DEFAULT NULL, + RECOVERY_FLOW_ID VARCHAR(255), + PRIMARY KEY(USER_NAME, USER_DOMAIN, TENANT_ID, SCENARIO,STEP), + FOREIGN KEY (RECOVERY_FLOW_ID) REFERENCES IDN_RECOVERY_FLOW_DATA(RECOVERY_FLOW_ID) ON DELETE CASCADE, + UNIQUE(CODE) +); + +CREATE TABLE IF NOT EXISTS IDN_PASSWORD_HISTORY_DATA ( + ID INTEGER NOT NULL AUTO_INCREMENT, + USER_NAME VARCHAR(255) NOT NULL, + USER_DOMAIN VARCHAR(127) NOT NULL, + TENANT_ID INTEGER DEFAULT -1, + SALT_VALUE VARCHAR(255), + HASH VARCHAR(255) NOT NULL, + TIME_CREATED TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, + PRIMARY KEY (ID), + UNIQUE (USER_NAME,USER_DOMAIN,TENANT_ID,SALT_VALUE,HASH) +); + +CREATE TABLE IF NOT EXISTS IDN_CLAIM_DIALECT ( + ID INTEGER NOT NULL AUTO_INCREMENT, + DIALECT_URI VARCHAR (255) NOT NULL, + TENANT_ID INTEGER NOT NULL, + PRIMARY KEY (ID), + CONSTRAINT DIALECT_URI_CONSTRAINT UNIQUE (DIALECT_URI, TENANT_ID) +); + +CREATE TABLE IF NOT EXISTS IDN_CLAIM ( + ID INTEGER NOT NULL AUTO_INCREMENT, + DIALECT_ID INTEGER NOT NULL, + CLAIM_URI VARCHAR (255) NOT NULL, + TENANT_ID INTEGER NOT NULL, + PRIMARY KEY (ID), + FOREIGN KEY (DIALECT_ID) REFERENCES IDN_CLAIM_DIALECT(ID) ON DELETE CASCADE, + CONSTRAINT CLAIM_URI_CONSTRAINT UNIQUE (DIALECT_ID, CLAIM_URI, TENANT_ID) +); + +CREATE TABLE IF NOT EXISTS IDN_CLAIM_MAPPED_ATTRIBUTE ( + ID INTEGER NOT NULL AUTO_INCREMENT, + LOCAL_CLAIM_ID INTEGER, + USER_STORE_DOMAIN_NAME VARCHAR (255) NOT NULL, + ATTRIBUTE_NAME VARCHAR (255) NOT NULL, + TENANT_ID INTEGER NOT NULL, + PRIMARY KEY (ID), + FOREIGN KEY (LOCAL_CLAIM_ID) REFERENCES IDN_CLAIM(ID) ON DELETE CASCADE, + CONSTRAINT USER_STORE_DOMAIN_CONSTRAINT UNIQUE (LOCAL_CLAIM_ID, USER_STORE_DOMAIN_NAME, TENANT_ID) +); + +CREATE TABLE IF NOT EXISTS IDN_CLAIM_PROPERTY ( + ID INTEGER NOT NULL AUTO_INCREMENT, + LOCAL_CLAIM_ID INTEGER, + PROPERTY_NAME VARCHAR (255) NOT NULL, + PROPERTY_VALUE VARCHAR (255) NOT NULL, + TENANT_ID INTEGER NOT NULL, + PRIMARY KEY (ID), + FOREIGN KEY (LOCAL_CLAIM_ID) REFERENCES IDN_CLAIM(ID) ON DELETE CASCADE, + CONSTRAINT PROPERTY_NAME_CONSTRAINT UNIQUE (LOCAL_CLAIM_ID, PROPERTY_NAME, TENANT_ID) +); + +CREATE TABLE IF NOT EXISTS IDN_CLAIM_MAPPING ( + ID INTEGER NOT NULL AUTO_INCREMENT, + EXT_CLAIM_ID INTEGER NOT NULL, + MAPPED_LOCAL_CLAIM_ID INTEGER NOT NULL, + TENANT_ID INTEGER NOT NULL, + PRIMARY KEY (ID), + FOREIGN KEY (EXT_CLAIM_ID) REFERENCES IDN_CLAIM(ID) ON DELETE CASCADE, + FOREIGN KEY (MAPPED_LOCAL_CLAIM_ID) REFERENCES IDN_CLAIM(ID) ON DELETE CASCADE, + CONSTRAINT EXT_TO_LOC_MAPPING_CONSTRN UNIQUE (EXT_CLAIM_ID, TENANT_ID) +); + +CREATE TABLE IF NOT EXISTS IDN_SAML2_ASSERTION_STORE ( + ID INTEGER NOT NULL AUTO_INCREMENT, + SAML2_ID VARCHAR(255) , + SAML2_ISSUER VARCHAR(255) , + SAML2_SUBJECT VARCHAR(255) , + SAML2_SESSION_INDEX VARCHAR(255) , + SAML2_AUTHN_CONTEXT_CLASS_REF VARCHAR(255) , + SAML2_ASSERTION VARCHAR(4096) , + ASSERTION BLOB , + PRIMARY KEY (ID) +); + +CREATE TABLE IDN_SAML2_ARTIFACT_STORE ( + ID INT NOT NULL AUTO_INCREMENT, + SOURCE_ID VARCHAR(255) NOT NULL, + MESSAGE_HANDLER VARCHAR(255) NOT NULL, + AUTHN_REQ_DTO BLOB NOT NULL, + SESSION_ID VARCHAR(255) NOT NULL, + INIT_TIMESTAMP TIMESTAMP NOT NULL, + EXP_TIMESTAMP TIMESTAMP NOT NULL, + ASSERTION_ID VARCHAR(255), + PRIMARY KEY (`ID`) +); + +CREATE TABLE IF NOT EXISTS IDN_OIDC_JTI ( + JWT_ID VARCHAR(255), + TENANT_ID INTEGER NOT NULL, + EXP_TIME TIMESTAMP NOT NULL , + TIME_CREATED TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP , + PRIMARY KEY (JWT_ID, TENANT_ID) +); + + +CREATE TABLE IF NOT EXISTS IDN_OIDC_PROPERTY ( + ID INTEGER NOT NULL AUTO_INCREMENT, + TENANT_ID INTEGER, + CONSUMER_KEY VARCHAR(255) , + PROPERTY_KEY VARCHAR(255) NOT NULL, + PROPERTY_VALUE VARCHAR(2047) , + PRIMARY KEY (ID), + FOREIGN KEY (TENANT_ID, CONSUMER_KEY) REFERENCES IDN_OAUTH_CONSUMER_APPS(TENANT_ID, CONSUMER_KEY) ON DELETE CASCADE +); +CREATE TABLE IF NOT EXISTS IDN_OIDC_REQ_OBJECT_REFERENCE ( + ID INTEGER NOT NULL AUTO_INCREMENT, + CONSUMER_KEY_ID INTEGER , + CODE_ID VARCHAR(255) , + TOKEN_ID VARCHAR(255) , + SESSION_DATA_KEY VARCHAR(255), + PRIMARY KEY (ID), + FOREIGN KEY (CONSUMER_KEY_ID) REFERENCES IDN_OAUTH_CONSUMER_APPS(ID) ON DELETE CASCADE, + FOREIGN KEY (TOKEN_ID) REFERENCES IDN_OAUTH2_ACCESS_TOKEN(TOKEN_ID) ON DELETE CASCADE, + FOREIGN KEY (CODE_ID) REFERENCES IDN_OAUTH2_AUTHORIZATION_CODE(CODE_ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDN_OIDC_REQ_OBJECT_CLAIMS ( + ID INTEGER NOT NULL AUTO_INCREMENT, + REQ_OBJECT_ID INTEGER, + CLAIM_ATTRIBUTE VARCHAR(255) , + ESSENTIAL CHAR(1) NOT NULL DEFAULT '0', + `VALUE` VARCHAR(255) , + IS_USERINFO CHAR(1) NOT NULL DEFAULT '0', + PRIMARY KEY (ID), + FOREIGN KEY (REQ_OBJECT_ID) REFERENCES IDN_OIDC_REQ_OBJECT_REFERENCE (ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDN_OIDC_REQ_OBJ_CLAIM_VALUES ( + ID INTEGER NOT NULL AUTO_INCREMENT, + REQ_OBJECT_CLAIMS_ID INTEGER , + CLAIM_VALUES VARCHAR(255) , + PRIMARY KEY (ID), + FOREIGN KEY (REQ_OBJECT_CLAIMS_ID) REFERENCES IDN_OIDC_REQ_OBJECT_CLAIMS(ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDN_CERTIFICATE ( + ID INTEGER NOT NULL AUTO_INCREMENT, + NAME VARCHAR(100), + CERTIFICATE_IN_PEM BLOB, + TENANT_ID INTEGER DEFAULT 0, + PRIMARY KEY(ID), + CONSTRAINT CERTIFICATE_UNIQUE_KEY UNIQUE (NAME, TENANT_ID) +); + +CREATE TABLE IF NOT EXISTS IDN_OIDC_SCOPE_CLAIM_MAPPING ( + ID INTEGER NOT NULL AUTO_INCREMENT, + SCOPE_ID INTEGER NOT NULL, + EXTERNAL_CLAIM_ID INTEGER NOT NULL, + PRIMARY KEY (ID), + FOREIGN KEY (SCOPE_ID) REFERENCES IDN_OAUTH2_SCOPE(SCOPE_ID) ON DELETE CASCADE, + FOREIGN KEY (EXTERNAL_CLAIM_ID) REFERENCES IDN_CLAIM(ID) ON DELETE CASCADE, + UNIQUE (SCOPE_ID, EXTERNAL_CLAIM_ID) +); + +CREATE TABLE IF NOT EXISTS IDN_FUNCTION_LIBRARY ( + NAME VARCHAR(255) NOT NULL, + DESCRIPTION VARCHAR(1023), + TYPE VARCHAR(255) NOT NULL, + TENANT_ID INTEGER NOT NULL, + DATA BLOB NOT NULL, + PRIMARY KEY (TENANT_ID,NAME) +); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH2_CIBA_AUTH_CODE ( + AUTH_CODE_KEY CHAR (36), + AUTH_REQ_ID CHAR (36), + ISSUED_TIME TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, + CONSUMER_KEY VARCHAR(255), + LAST_POLLED_TIME TIMESTAMP NOT NULL, + POLLING_INTERVAL INTEGER, + EXPIRES_IN INTEGER, + AUTHENTICATED_USER_NAME VARCHAR(255), + USER_STORE_DOMAIN VARCHAR(100), + TENANT_ID INTEGER, + AUTH_REQ_STATUS VARCHAR (100) DEFAULT 'REQUESTED', + IDP_ID INTEGER, + UNIQUE(AUTH_REQ_ID), + PRIMARY KEY (AUTH_CODE_KEY), + FOREIGN KEY (TENANT_ID, CONSUMER_KEY) REFERENCES IDN_OAUTH_CONSUMER_APPS(TENANT_ID, CONSUMER_KEY) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH2_CIBA_REQUEST_SCOPES ( + ID INTEGER NOT NULL AUTO_INCREMENT, + AUTH_CODE_KEY CHAR (36), + SCOPE VARCHAR (255), + FOREIGN KEY (AUTH_CODE_KEY) REFERENCES IDN_OAUTH2_CIBA_AUTH_CODE(AUTH_CODE_KEY) ON DELETE CASCADE, + PRIMARY KEY (ID) +); + +CREATE TABLE IF NOT EXISTS IDN_FED_AUTH_SESSION_MAPPING ( + ID INTEGER NOT NULL AUTO_INCREMENT, + IDP_SESSION_ID VARCHAR(255) NOT NULL, + SESSION_ID VARCHAR(255) NOT NULL, + IDP_NAME VARCHAR(255) NOT NULL, + AUTHENTICATOR_ID VARCHAR(255), + PROTOCOL_TYPE VARCHAR(255), + TIME_CREATED TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, + TENANT_ID INTEGER NOT NULL DEFAULT 0, + IDP_ID INTEGER NOT NULL DEFAULT 0, + FOREIGN KEY (IDP_ID) REFERENCES IDP(ID) ON DELETE CASCADE, + PRIMARY KEY (ID), + UNIQUE (IDP_SESSION_ID, TENANT_ID, IDP_ID) +); + +CREATE TABLE IF NOT EXISTS IDN_CONFIG_TYPE ( + ID VARCHAR(255) NOT NULL, + NAME VARCHAR(255) NOT NULL, + DESCRIPTION VARCHAR(1023) NULL, + PRIMARY KEY (ID), + CONSTRAINT TYPE_NAME_CONSTRAINT UNIQUE (NAME) +); + +INSERT INTO IDN_CONFIG_TYPE (ID, NAME, DESCRIPTION) VALUES +('9ab0ef95-13e9-4ed5-afaf-d29bed62f7bd', 'IDP_TEMPLATE', 'Template type to uniquely identify IDP templates'), +('3c4ac3d0-5903-4e3d-aaca-38df65b33bfd', 'APPLICATION_TEMPLATE', 'Template type to uniquely identify Application templates'), +('8ec6dbf1-218a-49bf-bc34-0d2db52d151c', 'CORS_CONFIGURATION', 'A resource type to keep the tenant CORS configurations'), +('669b99ca-cdb0-44a6-8cae-babed3b585df', 'Publisher', 'A resource type to keep the event publisher configurations'), +('73f6d9ca-62f4-4566-bab9-2a930ae51ba8', 'BRANDING_PREFERENCES', 'A resource type to keep the tenant branding preferences'), +('8469a176-3e6c-438a-ba01-71e9077072fa', 'APPLICATION_BRANDING_PREFERENCES', 'A resource type to keep the application branding preferences'), +('899c69b2-8bf7-46b5-9666-f7f99f90d6cc', 'fido-config', 'A resource type to store FIDO authenticator related preferences'), +('7f24050f-3e3d-4a00-b10f-fd5450d6523e', 'input-validation-configurations', 'A resource type to store input validation related configurations'), +('f4e83b8a-d1c4-a0d6-03a7-d48e268c60c5', 'PK_JWT_CONFIGURATION', 'A resource type to keep the tenant private key jwt configuration.'), +('9ec61e9d-f0e6-4952-9a09-ab842aeb2db2', 'ATTRIBUTE_CONFIGURATION', 'A resource type to store attribute related configurations.'), +('132b0ee6-43e0-462d-8b4b-15b68109d71d', 'ORGANIZATION_CONFIGURATION', 'A resource type to keep the organization configurations.'), +('1fc809a0-dc0d-4cb2-82f3-58934d389236', 'CUSTOM_TEXT', 'A resource type to keep the tenant custom text preferences.'), +('c385a42a-5697-4604-b49a-62456621e926', 'DCR_CONFIGURATION', 'A resource type to keep the DCR configurations.'), +('3e5b1f91-72d8-4fbc-94d1-1b9a4f8c3b07', 'IMPERSONATION_CONFIGURATION', 'A resource type to keep the tenant impersonation preferences.'); + +CREATE TABLE IF NOT EXISTS IDN_CONFIG_RESOURCE ( + ID VARCHAR(255) NOT NULL, + TENANT_ID INT NOT NULL, + NAME VARCHAR(255) NOT NULL, + CREATED_TIME TIMESTAMP NOT NULL, + LAST_MODIFIED TIMESTAMP NOT NULL, + HAS_FILE BOOLEAN NOT NULL, + HAS_ATTRIBUTE BOOLEAN NOT NULL, + TYPE_ID VARCHAR(255) NOT NULL, + UNIQUE (NAME, TENANT_ID, TYPE_ID), + PRIMARY KEY (ID) +); +ALTER TABLE IDN_CONFIG_RESOURCE +ADD CONSTRAINT TYPE_ID_FOREIGN_CONSTRAINT FOREIGN KEY (TYPE_ID) REFERENCES IDN_CONFIG_TYPE (ID) +ON DELETE CASCADE ON UPDATE CASCADE; + +CREATE TABLE IF NOT EXISTS IDN_CONFIG_ATTRIBUTE ( + ID VARCHAR(255) NOT NULL, + RESOURCE_ID VARCHAR(255) NOT NULL, + ATTR_KEY VARCHAR(255) NOT NULL, + ATTR_VALUE VARCHAR(1023) NULL, + PRIMARY KEY (ID), + UNIQUE (RESOURCE_ID, ATTR_KEY) +); +ALTER TABLE IDN_CONFIG_ATTRIBUTE +ADD CONSTRAINT RESOURCE_ID_ATTRIBUTE_FOREIGN_CONSTRAINT FOREIGN KEY (RESOURCE_ID) REFERENCES +IDN_CONFIG_RESOURCE (ID) ON DELETE CASCADE ON UPDATE CASCADE; + +CREATE TABLE IF NOT EXISTS IDN_CONFIG_FILE ( + ID VARCHAR(255) NOT NULL, + `VALUE` BLOB NULL, + RESOURCE_ID VARCHAR(255) NOT NULL, + NAME VARCHAR(255) NULL, + PRIMARY KEY (ID) +); +ALTER TABLE IDN_CONFIG_FILE +ADD CONSTRAINT RESOURCE_ID_FILE_FOREIGN_CONSTRAINT FOREIGN KEY (RESOURCE_ID) REFERENCES +IDN_CONFIG_RESOURCE (ID) ON DELETE CASCADE ON UPDATE CASCADE; + +CREATE TABLE IF NOT EXISTS IDN_REMOTE_FETCH_CONFIG ( + ID VARCHAR(255) NOT NULL, + TENANT_ID INTEGER NOT NULL, + IS_ENABLED CHAR(1) NOT NULL, + REPO_MANAGER_TYPE VARCHAR(255) NOT NULL, + ACTION_LISTENER_TYPE VARCHAR(255) NOT NULL, + CONFIG_DEPLOYER_TYPE VARCHAR(255) NOT NULL, + REMOTE_FETCH_NAME VARCHAR(255), + REMOTE_RESOURCE_URI VARCHAR(255) NOT NULL, + ATTRIBUTES_JSON MEDIUMTEXT NOT NULL, + PRIMARY KEY (ID), + CONSTRAINT UC_REMOTE_RESOURCE_TYPE UNIQUE (TENANT_ID, CONFIG_DEPLOYER_TYPE) +); + +CREATE TABLE IF NOT EXISTS IDN_REMOTE_FETCH_REVISIONS ( + ID VARCHAR(255) NOT NULL, + CONFIG_ID VARCHAR(255) NOT NULL, + FILE_PATH VARCHAR(255) NOT NULL, + FILE_HASH VARCHAR(255), + DEPLOYED_DATE TIMESTAMP, + LAST_SYNC_TIME TIMESTAMP, + DEPLOYMENT_STATUS VARCHAR(255), + ITEM_NAME VARCHAR(255), + DEPLOY_ERR_LOG MEDIUMTEXT, + PRIMARY KEY (ID), + FOREIGN KEY (CONFIG_ID) REFERENCES IDN_REMOTE_FETCH_CONFIG(ID) ON DELETE CASCADE, + CONSTRAINT UC_REVISIONS UNIQUE (CONFIG_ID, ITEM_NAME) +); + + +CREATE TABLE IF NOT EXISTS IDN_USER_FUNCTIONALITY_MAPPING ( + ID VARCHAR(255) NOT NULL, + USER_ID VARCHAR(255) NOT NULL, + TENANT_ID INTEGER NOT NULL, + FUNCTIONALITY_ID VARCHAR(255) NOT NULL, + IS_FUNCTIONALITY_LOCKED BOOLEAN NOT NULL, + FUNCTIONALITY_UNLOCK_TIME BIGINT NOT NULL, + FUNCTIONALITY_LOCK_REASON VARCHAR(1023), + FUNCTIONALITY_LOCK_REASON_CODE VARCHAR(255), + PRIMARY KEY (ID), + CONSTRAINT IDN_USER_FUNCTIONALITY_MAPPING_CONSTRAINT UNIQUE (USER_ID, TENANT_ID, FUNCTIONALITY_ID) +); + +CREATE TABLE IF NOT EXISTS IDN_USER_FUNCTIONALITY_PROPERTY ( + ID VARCHAR(255) NOT NULL, + USER_ID VARCHAR(255) NOT NULL, + TENANT_ID INTEGER NOT NULL, + FUNCTIONALITY_ID VARCHAR(255) NOT NULL, + PROPERTY_NAME VARCHAR(255), + PROPERTY_VALUE VARCHAR(255), + PRIMARY KEY (ID), + CONSTRAINT IDN_USER_FUNCTIONALITY_PROPERTY_CONSTRAINT UNIQUE (USER_ID, TENANT_ID, FUNCTIONALITY_ID, PROPERTY_NAME) +); + +CREATE TABLE IF NOT EXISTS IDN_CORS_ORIGIN ( + ID INT NOT NULL AUTO_INCREMENT, + TENANT_ID INT NOT NULL, + ORIGIN VARCHAR(2048) NOT NULL, + UUID CHAR(36) NOT NULL, + + PRIMARY KEY (ID), + UNIQUE (TENANT_ID, ORIGIN), + UNIQUE (UUID) +); + +CREATE TABLE IF NOT EXISTS IDN_CORS_ASSOCIATION ( + IDN_CORS_ORIGIN_ID INT NOT NULL, + SP_APP_ID INT NOT NULL, + + PRIMARY KEY (IDN_CORS_ORIGIN_ID, SP_APP_ID), + FOREIGN KEY (IDN_CORS_ORIGIN_ID) REFERENCES IDN_CORS_ORIGIN (ID) ON DELETE CASCADE, + FOREIGN KEY (SP_APP_ID) REFERENCES SP_APP (ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH2_USER_CONSENT ( + ID INTEGER NOT NULL AUTO_INCREMENT, + USER_ID VARCHAR(255) NOT NULL, + APP_ID CHAR(36) NOT NULL, + TENANT_ID INTEGER NOT NULL DEFAULT -1, + CONSENT_ID VARCHAR(255) NOT NULL, + PRIMARY KEY (ID), + FOREIGN KEY (APP_ID) REFERENCES SP_APP(UUID) ON DELETE CASCADE, + UNIQUE (USER_ID, APP_ID, TENANT_ID), + UNIQUE (CONSENT_ID) +); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH2_USER_CONSENTED_SCOPES ( + ID INTEGER NOT NULL AUTO_INCREMENT, + CONSENT_ID VARCHAR(255) NOT NULL, + TENANT_ID INTEGER NOT NULL DEFAULT -1, + SCOPE VARCHAR(255) NOT NULL, + CONSENT BOOLEAN NOT NULL, + PRIMARY KEY (ID), + FOREIGN KEY (CONSENT_ID) REFERENCES IDN_OAUTH2_USER_CONSENT(CONSENT_ID) ON DELETE CASCADE, + UNIQUE (CONSENT_ID, SCOPE) +); + +CREATE TABLE IF NOT EXISTS IDN_SECRET_TYPE ( + ID VARCHAR(255) NOT NULL, + NAME VARCHAR(255) NOT NULL, + DESCRIPTION VARCHAR(1023) NULL, + PRIMARY KEY (ID), + CONSTRAINT SECRET_TYPE_NAME_CONSTRAINT UNIQUE (NAME) +); + +INSERT INTO IDN_SECRET_TYPE (ID, NAME, DESCRIPTION) VALUES +('1358bdbf-e0cc-4268-a42c-c3e0960e13f0', 'ADAPTIVE_AUTH_CALL_CHOREO', 'Secret type to uniquely identify secrets relevant to callChoreo adaptive auth function'), +('c508ca28-60c0-4493-a758-77e4173ffdb9', 'IDP_SECRET_PROPERTIES', 'Secret type to uniquely identify secrets relevant to identity providers'), +('433df096-62b7-4a36-b3eb-1bed9150ed35', 'IDVP_SECRET_PROPERTIES', 'Secret type to uniquely identify secrets relevant to identity verification providers'), +('29d0c37d-139a-4b1e-a343-7b8d26f0a2a9', 'ANDROID_ATTESTATION_CREDENTIALS', 'Secret type to uniquely identify secrets relevant to android client attestation credentials'), +('33f0a41b-569d-4ea5-a891-6c0e78a1c3b0', 'ACTION_API_ENDPOINT_AUTH_SECRETS', 'Secret type to uniquely identify secrets relevant to action endpoint authentication properties'); + +CREATE TABLE IF NOT EXISTS IDN_SECRET ( + ID VARCHAR(255) NOT NULL, + TENANT_ID INT NOT NULL, + SECRET_NAME VARCHAR(1023) NOT NULL, + SECRET_VALUE VARCHAR(8000) NOT NULL, + CREATED_TIME TIMESTAMP NOT NULL, + LAST_MODIFIED TIMESTAMP NOT NULL, + TYPE_ID VARCHAR(255) NOT NULL, + DESCRIPTION VARCHAR(1023) NULL, + KEY_ID VARCHAR(255) NULL, + PRIMARY KEY (ID), + FOREIGN KEY (TYPE_ID) REFERENCES IDN_SECRET_TYPE(ID) ON DELETE CASCADE, + UNIQUE (SECRET_NAME, TENANT_ID, TYPE_ID) +); + +CREATE TABLE IF NOT EXISTS SP_SHARED_APP ( + ID INTEGER NOT NULL AUTO_INCREMENT, + MAIN_APP_ID CHAR(36) NOT NULL, + OWNER_ORG_ID CHAR(36) NOT NULL, + SHARED_APP_ID CHAR(36) NOT NULL, + SHARED_ORG_ID CHAR(36) NOT NULL, + SHARE_WITH_ALL_CHILDREN BOOLEAN DEFAULT FALSE, + PRIMARY KEY (ID), + FOREIGN KEY (MAIN_APP_ID) REFERENCES SP_APP(UUID) ON DELETE CASCADE, + FOREIGN KEY (SHARED_APP_ID) REFERENCES SP_APP(UUID) ON DELETE CASCADE, + UNIQUE (MAIN_APP_ID, OWNER_ORG_ID, SHARED_ORG_ID), + UNIQUE (SHARED_APP_ID) +); + +CREATE TABLE IF NOT EXISTS IDVP ( + ID INTEGER NOT NULL AUTO_INCREMENT, + UUID CHAR(36) NOT NULL, + TENANT_ID INTEGER NOT NULL, + IDVP_TYPE VARCHAR(254), + NAME VARCHAR(254), + DESCRIPTION VARCHAR(1024), + IS_ENABLED CHAR(1) NOT NULL DEFAULT '0', + PRIMARY KEY (ID), + UNIQUE (TENANT_ID, NAME), + UNIQUE (UUID) +); + +CREATE TABLE IF NOT EXISTS IDVP_CLAIM_MAPPING ( + ID INTEGER NOT NULL AUTO_INCREMENT, + IDVP_ID INTEGER NOT NULL, + TENANT_ID INTEGER NOT NULL, + CLAIM VARCHAR(254), + LOCAL_CLAIM VARCHAR(254), + PRIMARY KEY (ID), + UNIQUE (IDVP_ID, CLAIM, TENANT_ID), + FOREIGN KEY (IDVP_ID) REFERENCES IDVP(ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDVP_CONFIG ( + ID INTEGER NOT NULL AUTO_INCREMENT, + IDVP_ID INTEGER NOT NULL, + TENANT_ID INTEGER NOT NULL, + PROPERTY_KEY VARCHAR(254) NOT NULL, + PROPERTY_VALUE VARCHAR(1024), + IS_SECRET CHAR (1) DEFAULT '0', + PRIMARY KEY (ID), + UNIQUE (IDVP_ID, PROPERTY_KEY, TENANT_ID), + FOREIGN KEY (IDVP_ID) REFERENCES IDVP(ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDV_CLAIM ( + ID INTEGER NOT NULL AUTO_INCREMENT, + UUID CHAR(36) NOT NULL, + USER_ID VARCHAR(254) NOT NULL, + CLAIM_URI VARCHAR(254), + IDVP_ID CHAR(36) NOT NULL, + TENANT_ID INTEGER NOT NULL, + IS_VERIFIED CHAR(1) NOT NULL DEFAULT '0', + METADATA BLOB, + PRIMARY KEY (ID), + UNIQUE (CLAIM_URI, TENANT_ID, USER_ID, IDVP_ID), + UNIQUE (UUID), + FOREIGN KEY (IDVP_ID) REFERENCES IDVP(UUID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS IDN_OAUTH_PAR ( + REQ_URI_REF VARCHAR(255) PRIMARY KEY, + CLIENT_ID VARCHAR(255) NOT NULL, + SCHEDULED_EXPIRY BIGINT NOT NULL, + PARAMETERS MEDIUMTEXT +); + +CREATE TABLE IF NOT EXISTS IDN_ORG_USER_INVITATION ( + ID INTEGER NOT NULL AUTO_INCREMENT, + INVITATION_ID VARCHAR(40) NOT NULL, + CONFIRMATION_CODE VARCHAR(40) NOT NULL, + USER_NAME VARCHAR(254) NOT NULL, + DOMAIN_NAME VARCHAR(254) NOT NULL, + EMAIL VARCHAR(254) NOT NULL, + USER_ORG_ID VARCHAR(254) NOT NULL, + INVITED_ORG_ID VARCHAR(254) NOT NULL, + USER_REDIRECT_URL VARCHAR(1024) NOT NULL, + STATUS VARCHAR(10) NOT NULL, + CREATED_AT TIMESTAMP NOT NULL, + EXPIRED_AT TIMESTAMP NOT NULL, + PRIMARY KEY (INVITATION_ID) +); + +CREATE TABLE IF NOT EXISTS IDN_ORG_USER_INVITE_ASSIGNMENT( + ID INTEGER NOT NULL AUTO_INCREMENT, + INVITATION_ID VARCHAR(40) NOT NULL, + ASSIGNMENT_ID VARCHAR(255) NOT NULL, + ASSIGNMENT_TYPE VARCHAR(255) NOT NULL, + PRIMARY KEY (INVITATION_ID, ASSIGNMENT_ID, ASSIGNMENT_TYPE), + FOREIGN KEY (INVITATION_ID) REFERENCES IDN_ORG_USER_INVITATION(INVITATION_ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS API_RESOURCE ( + ID CHAR(36) NOT NULL PRIMARY KEY, + CURSOR_KEY INTEGER NOT NULL AUTO_INCREMENT, + NAME VARCHAR(255) NOT NULL, + IDENTIFIER VARCHAR(255) NOT NULL, + TENANT_ID INT, + DESCRIPTION VARCHAR(255), + TYPE VARCHAR(255) NOT NULL, + REQUIRES_AUTHORIZATION BOOLEAN NOT NULL +); + +CREATE TABLE IF NOT EXISTS API_RESOURCE_PROPERTY ( + ID INTEGER AUTO_INCREMENT, + API_ID CHAR(36) NOT NULL, + NAME VARCHAR(255) NOT NULL, + `VALUE` VARCHAR(255) NOT NULL, + PRIMARY KEY (ID), + CONSTRAINT API_RESOURCE_PROPERTY_CONSTRAINT UNIQUE (API_ID, NAME), + FOREIGN KEY (API_ID) REFERENCES API_RESOURCE(ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS SCOPE ( + ID CHAR(36) NOT NULL PRIMARY KEY, + CURSOR_KEY INTEGER NOT NULL AUTO_INCREMENT, + API_ID CHAR(36) NOT NULL, + NAME VARCHAR(255) NOT NULL, + DISPLAY_NAME VARCHAR(255) NOT NULL, + TENANT_ID INT, + DESCRIPTION VARCHAR(300), + FOREIGN KEY (API_ID) REFERENCES API_RESOURCE(ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS APP_ROLE_ASSOCIATION ( + APP_ID CHAR(36) NOT NULL, + ROLE_ID VARCHAR(255) NOT NULL, + PRIMARY KEY (APP_ID, ROLE_ID), + FOREIGN KEY (APP_ID) REFERENCES SP_APP(UUID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS ROLE_SCOPE ( + ROLE_ID VARCHAR(255) NOT NULL, + SCOPE_ID CHAR(36) NOT NULL, + PRIMARY KEY (ROLE_ID, SCOPE_ID), + FOREIGN KEY (SCOPE_ID) REFERENCES SCOPE(ID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS AUTHORIZED_API( + APP_ID CHAR(36) NOT NULL, + API_ID CHAR(36) NOT NULL, + POLICY_ID VARCHAR(255) NOT NULL, + CONSTRAINT PK_APP_API PRIMARY KEY (APP_ID, API_ID), + FOREIGN KEY (API_ID) REFERENCES API_RESOURCE(ID) ON DELETE CASCADE, + FOREIGN KEY (APP_ID) REFERENCES SP_APP(UUID) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS AUTHORIZED_SCOPE( + APP_ID CHAR(36) NOT NULL, + API_ID CHAR(36) NOT NULL, + SCOPE_ID CHAR(36) NOT NULL, + CONSTRAINT PK_APP_API_SCOPE PRIMARY KEY (APP_ID, API_ID, SCOPE_ID), + FOREIGN KEY (API_ID) REFERENCES API_RESOURCE(ID), + FOREIGN KEY (SCOPE_ID) REFERENCES SCOPE(ID) ON DELETE CASCADE, + FOREIGN KEY (APP_ID) REFERENCES SP_APP(UUID), + FOREIGN KEY (APP_ID, API_ID) REFERENCES AUTHORIZED_API(APP_ID, API_ID) ON DELETE CASCADE, + CONSTRAINT AUTHORIZED_SCOPE_UNIQUE UNIQUE (APP_ID, SCOPE_ID) +); + +CREATE TABLE IF NOT EXISTS IDN_NOTIFICATION_TYPE ( + ID INTEGER NOT NULL AUTO_INCREMENT, + TYPE_KEY VARCHAR(255) NOT NULL, + NAME VARCHAR(255) NOT NULL, + CHANNEL VARCHAR(255) NOT NULL, + TENANT_ID INTEGER NOT NULL, + PRIMARY KEY (ID), + CONSTRAINT NOTIFICATION_TYPE_KEY_CONSTRAINT UNIQUE (TYPE_KEY, CHANNEL, TENANT_ID), + CONSTRAINT NOTIFICATION_TYPE_NAME_CONSTRAINT UNIQUE (NAME, CHANNEL, TENANT_ID) +); + +CREATE TABLE IF NOT EXISTS IDN_NOTIFICATION_ORG_TEMPLATE ( + ID INTEGER NOT NULL AUTO_INCREMENT, + TEMPLATE_KEY VARCHAR(50) NOT NULL, + LOCALE VARCHAR(50) NOT NULL, + SUBJECT VARCHAR(4000), + BODY MEDIUMTEXT, + FOOTER MEDIUMTEXT, + CONTENT_TYPE VARCHAR(50), + TYPE_ID INTEGER NOT NULL, + TENANT_ID INTEGER NOT NULL, + PRIMARY KEY (ID), + FOREIGN KEY (TYPE_ID) REFERENCES IDN_NOTIFICATION_TYPE(ID) ON DELETE CASCADE, + CONSTRAINT ORG_NOTIFICATION_TEMPLATE_KEY_CONSTRAINT UNIQUE (TEMPLATE_KEY, TYPE_ID, TENANT_ID), + CONSTRAINT ORG_NOTIFICATION_TEMPLATE_LOCALE_CONSTRAINT UNIQUE (LOCALE, TYPE_ID, TENANT_ID) +); + +CREATE TABLE IF NOT EXISTS IDN_NOTIFICATION_APP_TEMPLATE ( + ID INTEGER NOT NULL AUTO_INCREMENT, + TEMPLATE_KEY VARCHAR(50) NOT NULL, + LOCALE VARCHAR(50) NOT NULL, + SUBJECT VARCHAR(4000), + BODY MEDIUMTEXT, + FOOTER MEDIUMTEXT, + CONTENT_TYPE VARCHAR(50), + TYPE_ID INTEGER NOT NULL, + APP_ID VARCHAR(255) NOT NULL, + TENANT_ID INTEGER NOT NULL, + PRIMARY KEY (ID), + FOREIGN KEY (TYPE_ID) REFERENCES IDN_NOTIFICATION_TYPE(ID) ON DELETE CASCADE, + CONSTRAINT APP_NOTIFICATION_TEMPLATE_KEY_CONSTRAINT UNIQUE (TEMPLATE_KEY, TYPE_ID, APP_ID, TENANT_ID), + CONSTRAINT APP_NOTIFICATION_TEMPLATE_LOCALE_CONSTRAINT UNIQUE (LOCALE, TYPE_ID, APP_ID, TENANT_ID) +); + +CREATE TABLE IF NOT EXISTS IDN_ACTION ( + UUID CHAR(36) NOT NULL, + TYPE VARCHAR(50) NOT NULL, + NAME VARCHAR(255) NOT NULL, + DESCRIPTION VARCHAR(255), + STATUS VARCHAR(10) NOT NULL, + TENANT_ID INTEGER NOT NULL, + PRIMARY KEY (UUID) +); + +CREATE TABLE IF NOT EXISTS IDN_ACTION_ENDPOINT ( + ACTION_UUID CHAR(36) NOT NULL, + PROPERTY_NAME VARCHAR(100) NOT NULL, + PROPERTY_VALUE VARCHAR(255) NOT NULL, + TENANT_ID INTEGER NOT NULL, + PRIMARY KEY (ACTION_UUID, PROPERTY_NAME), + FOREIGN KEY (ACTION_UUID) REFERENCES IDN_ACTION(UUID) ON DELETE CASCADE +); + +-- --------------------------- INDEX CREATION ----------------------------- +-- IDN_OAUTH2_ACCESS_TOKEN -- +CREATE INDEX IDX_TC ON IDN_OAUTH2_ACCESS_TOKEN(TIME_CREATED); +CREATE INDEX IDX_ATH ON IDN_OAUTH2_ACCESS_TOKEN(ACCESS_TOKEN_HASH); +CREATE INDEX IDX_AT_TI_UD ON IDN_OAUTH2_ACCESS_TOKEN(AUTHZ_USER, TENANT_ID, TOKEN_STATE, USER_DOMAIN); +CREATE INDEX IDX_AT_AT ON IDN_OAUTH2_ACCESS_TOKEN(ACCESS_TOKEN); +CREATE INDEX IDX_AT_RTH ON IDN_OAUTH2_ACCESS_TOKEN(REFRESH_TOKEN_HASH); +CREATE INDEX IDX_AT_RT ON IDN_OAUTH2_ACCESS_TOKEN(REFRESH_TOKEN); +CREATE INDEX IDX_TBR_TS ON IDN_OAUTH2_ACCESS_TOKEN(TOKEN_BINDING_REF, TOKEN_STATE); + +-- IDN_OAUTH2_AUTHORIZATION_CODE -- +CREATE INDEX IDX_AUTHORIZATION_CODE_HASH ON IDN_OAUTH2_AUTHORIZATION_CODE (AUTHORIZATION_CODE_HASH, CONSUMER_KEY_ID); +CREATE INDEX IDX_AUTHORIZATION_CODE_AU_TI ON IDN_OAUTH2_AUTHORIZATION_CODE (AUTHZ_USER, TENANT_ID, USER_DOMAIN, STATE); +CREATE INDEX IDX_AC_CKID ON IDN_OAUTH2_AUTHORIZATION_CODE(CONSUMER_KEY_ID); +CREATE INDEX IDX_AC_TID ON IDN_OAUTH2_AUTHORIZATION_CODE(TOKEN_ID); +CREATE INDEX IDX_AC_AC_CKID ON IDN_OAUTH2_AUTHORIZATION_CODE(AUTHORIZATION_CODE, CONSUMER_KEY_ID); +CREATE INDEX IDX_AT_CKID_AU_TID_UD_TSH_TS ON IDN_OAUTH2_ACCESS_TOKEN(CONSUMER_KEY_ID, AUTHZ_USER, TENANT_ID, USER_DOMAIN, TOKEN_SCOPE_HASH, TOKEN_STATE); + +-- IDN_SCIM_GROUP -- +CREATE INDEX IDX_IDN_SCIM_GROUP_TI_RN ON IDN_SCIM_GROUP (TENANT_ID, ROLE_NAME); +CREATE INDEX IDX_IDN_SCIM_GROUP_TI_RN_AN ON IDN_SCIM_GROUP (TENANT_ID, ROLE_NAME, ATTR_NAME); + +-- IDN_AUTH_SESSION_STORE -- +CREATE INDEX IDX_IDN_AUTH_SESSION_TIME ON IDN_AUTH_SESSION_STORE (TIME_CREATED); +CREATE INDEX IDX_IDN_AUTH_SSTR_ST_OP_ID_TM ON IDN_AUTH_SESSION_STORE (OPERATION, SESSION_TYPE, SESSION_ID, TIME_CREATED); +CREATE INDEX IDX_IDN_AUTH_SSTR_ET_ID ON IDN_AUTH_SESSION_STORE (EXPIRY_TIME, SESSION_ID); + +-- IDN_AUTH_TEMP_SESSION_STORE -- +CREATE INDEX IDX_IDN_AUTH_TMP_SESSION_TIME ON IDN_AUTH_TEMP_SESSION_STORE (TIME_CREATED); + +-- IDN_OIDC_SCOPE_CLAIM_MAPPING -- +CREATE INDEX IDX_AT_SI_ECI ON IDN_OIDC_SCOPE_CLAIM_MAPPING(SCOPE_ID, EXTERNAL_CLAIM_ID); + +-- IDN_OAUTH2_SCOPE -- +CREATE INDEX IDX_SC_TID ON IDN_OAUTH2_SCOPE(TENANT_ID); + +-- IDN_OAUTH2_SCOPE_BINDING -- +CREATE INDEX IDX_SB_SCPID ON IDN_OAUTH2_SCOPE_BINDING(SCOPE_ID); + +-- IDN_OIDC_REQ_OBJECT_REFERENCE -- +CREATE INDEX IDX_OROR_TID ON IDN_OIDC_REQ_OBJECT_REFERENCE(TOKEN_ID); + +-- IDN_OAUTH2_ACCESS_TOKEN_SCOPE -- +CREATE INDEX IDX_ATS_TID ON IDN_OAUTH2_ACCESS_TOKEN_SCOPE(TOKEN_ID); + +-- SP_TEMPLATE -- +CREATE INDEX IDX_SP_TEMPLATE ON SP_TEMPLATE (TENANT_ID, NAME); + +-- IDN_AUTH_USER -- +CREATE INDEX IDX_AUTH_USER_UN_TID_DN ON IDN_AUTH_USER (USER_NAME, TENANT_ID, DOMAIN_NAME); +CREATE INDEX IDX_AUTH_USER_DN_TOD ON IDN_AUTH_USER (DOMAIN_NAME, TENANT_ID); + +-- IDN_AUTH_USER_SESSION_MAPPING -- +CREATE INDEX IDX_USER_ID ON IDN_AUTH_USER_SESSION_MAPPING (USER_ID); +CREATE INDEX IDX_SESSION_ID ON IDN_AUTH_USER_SESSION_MAPPING (SESSION_ID); + +-- IDN_AUTH_SESSION_APP_INFO -- +CREATE INDEX IDX_AUTH_SAI_UN_AID_SID ON IDN_AUTH_SESSION_APP_INFO (APP_ID, SUBJECT, SESSION_ID); + +-- IDN_OAUTH_CONSUMER_APPS -- +CREATE INDEX IDX_OCA_UM_TID_UD_APN ON IDN_OAUTH_CONSUMER_APPS(USERNAME,TENANT_ID,USER_DOMAIN, APP_NAME); + +-- IDX_SPI_APP -- +CREATE INDEX IDX_SPI_APP ON SP_INBOUND_AUTH(APP_ID); + +-- IDN_OIDC_PROPERTY -- +CREATE INDEX IDX_IOP_CK ON IDN_OIDC_PROPERTY(TENANT_ID, CONSUMER_KEY); + +-- IDN_FIDO2_PROPERTY -- +CREATE INDEX IDX_FIDO2_STR ON FIDO2_DEVICE_STORE(USER_NAME, TENANT_ID, DOMAIN_NAME, CREDENTIAL_ID, USER_HANDLE); + +-- IDN_ASSOCIATED_ID -- +CREATE INDEX IDX_AI_DN_UN_AI ON IDN_ASSOCIATED_ID(DOMAIN_NAME, USER_NAME, ASSOCIATION_ID); + +-- IDN_OAUTH2_TOKEN_BINDING -- +CREATE INDEX IDX_IDN_AUTH_BIND ON IDN_OAUTH2_TOKEN_BINDING (TOKEN_BINDING_REF); +CREATE INDEX IDX_TK_VALUE_TYPE ON IDN_OAUTH2_TOKEN_BINDING (TOKEN_BINDING_VALUE, TOKEN_BINDING_TYPE); + +-- IDN_FED_AUTH_SESSION_MAPPING -- +CREATE INDEX IDX_FEDERATED_AUTH_SESSION_ID ON IDN_FED_AUTH_SESSION_MAPPING (SESSION_ID); + +-- IDN_REMOTE_FETCH_REVISIONS -- +CREATE INDEX IDX_REMOTE_FETCH_REVISION_CONFIG_ID ON IDN_REMOTE_FETCH_REVISIONS (CONFIG_ID); + +-- IDN_CORS_ASSOCIATION -- +CREATE INDEX IDX_CORS_SP_APP_ID ON IDN_CORS_ASSOCIATION (SP_APP_ID); + +-- IDN_CORS_ASSOCIATION -- +CREATE INDEX IDX_CORS_ORIGIN_ID ON IDN_CORS_ASSOCIATION (IDN_CORS_ORIGIN_ID); + +-- IDN_SECRET -- +CREATE INDEX IDN_SECRET_TYPE_ID ON IDN_SECRET (TYPE_ID); + +-- IDN_CLAIM -- +CREATE INDEX IDX_CLAIM_TI_CU ON IDN_CLAIM (TENANT_ID, CLAIM_URI); + +-- IDP_AUTHENTICATOR_PROPERTY -- +CREATE INDEX IDX_AUTH_PROP_AUTH_ID ON IDP_AUTHENTICATOR_PROPERTY (AUTHENTICATOR_ID); + +-- IDN_CONFIG_FILE -- +CREATE INDEX IDX_CON_FILE_RES_ID ON IDN_CONFIG_FILE (RESOURCE_ID); + +-- SCOPE -- +CREATE INDEX API_ID_NAME_INDEX ON SCOPE (API_ID, NAME); + +-- ACTIONS -- +CREATE INDEX IDX_IDN_ACTION_TY_TI ON IDN_ACTION (TYPE, TENANT_ID); +CREATE INDEX IDX_IDN_ACTION_ENDPOINT_AU_TI ON IDN_ACTION_ENDPOINT (ACTION_UUID, TENANT_ID); diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/repository/conf/carbon.xml b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/repository/conf/carbon.xml new file mode 100644 index 000000000000..a5a1a6470cbc --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/repository/conf/carbon.xml @@ -0,0 +1,686 @@ + + + + + + + + WSO2 Identity Server + + + IS + + + 5.3.0 + + + localhost + + + localhost + + + local:/${carbon.context}/services/ + + + + + + + IdentityServer + + + + + + + org.wso2.carbon + + + / + + + + + + + + + 15 + + + + + + + + + 0 + + + + + 9999 + + 11111 + + + + + + 10389 + + 8000 + + + + + + 10500 + + + + + + + + + org.wso2.carbon.tomcat.jndi.CarbonJavaURLContextFactory + + + + + + + + + java + + + + + + + + + + false + + + false + + + 600 + + + + false + + + + + + + + 30 + + + + + + + + + 15 + + + + + + ${carbon.home}/repository/deployment/server/ + + + 15 + + + ${carbon.home}/repository/conf/axis2/axis2.xml + + + 30000 + + + ${carbon.home}/repository/deployment/client/ + + ${carbon.home}/repository/conf/axis2/axis2_client.xml + + true + + + + + + + + + + admin + Default Administrator Role + + + user + Default User Role + + + + + + + + + + + + ${carbon.home}/repository/resources/security/wso2carbon.jks + + JKS + + wso2carbon + + wso2carbon + + wso2carbon + + + + + + ${carbon.home}/repository/resources/security/client-truststore.jks + + JKS + + wso2carbon + + + + + + + + + + + + + + + + + + + UserManager + + + false + + org.wso2.carbon.identity.provider.AttributeCallbackHandler + + + org.wso2.carbon.identity.sts.store.DBTokenStore + + + true + allow + + + + + + + claim_mgt_menu + identity_mgt_emailtemplate_menu + identity_security_questions_menu + + + + ${carbon.home}/tmp/work + + + + + + true + + + 10 + + + 30 + + + + + + 100 + + + + keystore + certificate + * + + org.wso2.carbon.ui.transports.fileupload.AnyFileUploadExecutor + + + + + jarZip + + org.wso2.carbon.ui.transports.fileupload.JarZipUploadExecutor + + + + dbs + + org.wso2.carbon.ui.transports.fileupload.DBSFileUploadExecutor + + + + tools + + org.wso2.carbon.ui.transports.fileupload.ToolsFileUploadExecutor + + + + toolsAny + + org.wso2.carbon.ui.transports.fileupload.ToolsAnyFileUploadExecutor + + + + + + + + + + info + org.wso2.carbon.core.transports.util.InfoProcessor + + + wsdl + org.wso2.carbon.core.transports.util.Wsdl11Processor + + + wsdl2 + org.wso2.carbon.core.transports.util.Wsdl20Processor + + + xsd + org.wso2.carbon.core.transports.util.XsdProcessor + + + + + + false + false + true + svn + http://svnrepo.example.com/repos/ + username + password + true + + + + + + + + + + + + + + + ${require.carbon.servlet} + + + + + true + + + + + + + default repository + http://product-dist.wso2.com/p2/carbon/releases/wilkes/ + + + + + + + + true + + + + + + true + + diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/repository/conf/identity/identity.xml b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/repository/conf/identity/identity.xml new file mode 100644 index 000000000000..07de6831dbf4 --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/repository/conf/identity/identity.xml @@ -0,0 +1,743 @@ + + + + + + + + + jdbc/WSO2IdentityDB + + + + + true + true + 0 + + true + 20160 + 1140 + + + true + 720 + + + + + + + 15 + 20160 + + + + + + ${carbon.home}/conf/keystores + SunX509 + SunX509 + + + + SelfAndManaged + CertValidate + + + + + + + + + + + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/openidserver + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/openid + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/authenticationendpoint/openid_login.do + + + false + + 7200 + + false + + + + + + + + + + + + + + + + + + + + + + -1 + -1 + -1 + -1 + + + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/oauth/request-token + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/oauth/authorize-url + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/oauth/access-token + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/oauth2/authorize + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/oauth2/token + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/oauth2/revoke + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/oauth2/introspect + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/oauth2/userinfo + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/oidc/checksession + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/oidc/logout + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/authenticationendpoint/oauth2_authz.do + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/authenticationendpoint/oauth2_error.do + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/authenticationendpoint/oauth2_consent.do + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/authenticationendpoint/oauth2_logout_consent.do + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/authenticationendpoint/oauth2_logout.do + + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/.well-known/webfinger + + + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/identity/connect/register + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/oauth2/jwks + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/oauth2/oidcdiscovery + + + 300 + + 3600 + + 3600 + + 84600 + + 300 + + false + + true + + org.wso2.carbon.identity.oauth.tokenprocessor.PlainTextPersistenceProcessor + + + + false + + + + + + token + org.wso2.carbon.identity.oauth2.authz.handlers.AccessTokenResponseTypeHandler + + + code + org.wso2.carbon.identity.oauth2.authz.handlers.CodeResponseTypeHandler + + + id_token + org.wso2.carbon.identity.oauth2.authz.handlers.IDTokenResponseTypeHandler + + + id_token token + org.wso2.carbon.identity.oauth2.authz.handlers.IDTokenTokenResponseTypeHandler + + + + + + authorization_code + org.wso2.carbon.identity.oauth2.token.handlers.grant.AuthorizationCodeGrantHandler + + + password + org.wso2.carbon.identity.oauth2.token.handlers.grant.PasswordGrantHandler + + + refresh_token + org.wso2.carbon.identity.oauth2.token.handlers.grant.RefreshGrantHandler + + + client_credentials + org.wso2.carbon.identity.oauth2.token.handlers.grant.ClientCredentialsGrantHandler + + + urn:ietf:params:oauth:grant-type:saml2-bearer + org.wso2.carbon.identity.oauth2.token.handlers.grant.saml.SAML2BearerGrantHandler + + + iwa:ntlm + org.wso2.carbon.identity.oauth2.token.handlers.grant.iwa.ntlm.NTLMAuthenticationGrantHandler + + + idTokenNotAllowedGrantType + org.wso2.carbon.identity.oauth2.token.handlers.grant.idTokenNotAllowedGrantHandler + false + + + + + + + + + false + + + + false + + + + false + org.wso2.carbon.identity.oauth2.authcontext.JWTTokenGenerator + org.wso2.carbon.identity.oauth2.authcontext.DefaultClaimsRetriever + http://wso2.org/claims + SHA256withRSA + 10 + + + + + + org.wso2.carbon.identity.openidconnect.DefaultIDTokenBuilder + SHA256withRSA + + + + + + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/oauth2/token + org.wso2.carbon.identity.openidconnect.DefaultOIDCClaimsCallbackHandler + 3600 + org.wso2.carbon.identity.oauth.endpoint.user.impl.UserInfoUserStoreClaimRetriever + org.wso2.carbon.identity.oauth.endpoint.user.impl.UserInforRequestDefaultValidator + org.wso2.carbon.identity.oauth.endpoint.user.impl.UserInfoISAccessTokenValidator + org.wso2.carbon.identity.oauth.endpoint.user.impl.UserInfoJSONResponseBuilder + false + + + + + + + + gtalk + talk.google.com + 5222 + gmail.com + multifactor1@gmail.com + wso2carbon + + + + + + 157680000 + 157680000 + ${carbon.host} + + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/samlsso + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/authenticationendpoint/samlsso_logout.do + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/authenticationendpoint/samlsso_notification.do + 5 + 60000 + + false + http://wso2.org/claims + org.wso2.carbon.identity.sso.saml.builders.assertion.ExtendedDefaultAssertionBuilder + + org.wso2.carbon.identity.sso.saml.builders.encryption.DefaultSSOEncrypter + org.wso2.carbon.identity.sso.saml.builders.signature.DefaultSSOSigner + org.wso2.carbon.identity.sso.saml.validators.SAML2HTTPRedirectDeflateSignatureValidator + + + + 5 + false + http://www.w3.org/2000/09/xmldsig#rsa-sha1 + http://www.w3.org/2000/09/xmldsig#sha1 + true + + + + + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/services/wso2carbon-sts + + + + + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/passivests + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/authenticationendpoint/retry.do + org.wso2.carbon.identity.sts.passive.utils.NoPersistenceTokenStore + true + + + + + false + ${Ports.ThriftEntitlementReceivePort} + 10000 + + ${carbon.home}/repository/resources/security/wso2carbon.jks + wso2carbon + + + ${carbon.host} + + + + + + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/wso2/scim/Users + ${carbon.protocol}://${carbon.host}:${carbon.management.port}/wso2/scim/Groups + + + 5 + + + 10 + local://services + + + + + + + + + + + + + org.wso2.carbon.identity.governance.store.JDBCIdentityDataStore + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + /permission/admin/manage/identity/identitymgt + + + + + + /permission/admin/manage/identity/usermgt/view + + + /permission/admin/manage/identity/usermgt/view + + + + /permission/admin/manage/identity/configmgt/list + + + + /permission/admin/manage/identity/configmgt/add + + + /permission/admin/manage/identity/configmgt/update + + + + /permission/admin/manage/identity/configmgt/delete + + + + /permission/admin/manage/identity/configmgt/add + + + /permission/admin/manage/identity/configmgt/update + + + + /permission/admin/manage/identity/configmgt/delete + + + + /permission/admin/manage/identity/configmgt/add + + + /permission/admin/manage/identity/configmgt/update + + + + /permission/admin/manage/identity/configmgt/delete + + + + + + + /permission/admin/manage/identity/consentmgt/add + + + + /permission/admin/manage/identity/consentmgt/delete + + + + /permission/admin/manage/identity/consentmgt/add + + + + /permission/admin/manage/identity/consentmgt/delete + + + + /permission/admin/manage/identity/consentmgt/add + + + + /permission/admin/manage/identity/consentmgt/delete + + + + /permission/admin/manage/identity/identitymgt + + + + /permission/admin/manage/identity/applicationmgt/create + + + /permission/admin/manage/identity/applicationmgt/delete + + + /permission/admin/manage/identity/applicationmgt/update + + + /permission/admin/manage/identity/applicationmgt/view + + + /permission/admin/manage/identity/applicationmgt/delete + + + /permission/admin/manage/identity/applicationmgt/create + + + /permission/admin/manage/identity/applicationmgt/view + + + /permission/admin/manage/identity/pep + + + /permission/admin/manage/identity/usermgt/create + + + /permission/admin/manage/identity/usermgt/list + + + /permission/admin/manage/identity/rolemgt/create + + + /permission/admin/manage/identity/rolemgt/view + + + /permission/admin/manage/identity/usermgt/view + + + /permission/admin/manage/identity/usermgt/update + + + /permission/admin/manage/identity/usermgt/update + + + /permission/admin/manage/identity/usermgt/delete + + + /permission/admin/manage/identity/rolemgt/view + + + /permission/admin/manage/identity/rolemgt/update + + + /permission/admin/manage/identity/rolemgt/update + + + /permission/admin/manage/identity/rolemgt/delete + + + /permission/admin/login + + + /permission/admin/manage/identity/usermgt/delete + + + /permission/admin/login + + + /permission/admin/login + + + /permission/admin/manage/identity/usermgt/create + + + + + + + + + /permission/admin/manage/identity/usermgt + + + /permission/admin/manage/identity/applicationmgt + + + + + + + /permission/admin/manage/identity/usermgt/update + + + + + + /permission/admin/manage/humantask/viewtasks + + + /permission/admin/login + + + /permission/admin/manage/identity/usermgt + + + /permission/admin/manage/identity/ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + /api/identity/user/v0.9 + /api/identity/recovery/v0.9 + /oauth2 + /api/identity/entitlement + + + /identity/(.*) + + + + + + applications,connections + + + + 300 + diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/testng.xml b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/testng.xml index 917b616e3e8a..9512040a62d7 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/testng.xml +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/testng.xml @@ -22,6 +22,7 @@ + From 4a0a0b01f6cc9144f0874befbd5023a0166ab850 Mon Sep 17 00:00:00 2001 From: Thisara-Welmilla Date: Sun, 8 Dec 2024 18:14:38 +0530 Subject: [PATCH 04/15] Provide support for managing the user defined local authenticators, --- .../ApplicationAuthenticatorService.java | 25 ++++++++++++------- ...erDefinedFederatedAuthenticatorConfig.java | 2 +- .../UserDefinedLocalAuthenticatorConfig.java | 3 +-- 3 files changed, 18 insertions(+), 12 deletions(-) diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java index f1ec5c5aa264..1ed6e7001f3a 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java @@ -21,6 +21,7 @@ import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.wso2.carbon.identity.application.common.dao.impl.AuthenticatorManagementDAOImpl; +import org.wso2.carbon.identity.application.common.dao.AuthenticatorManagementDAO; import org.wso2.carbon.identity.application.common.dao.impl.CacheBackedAuthenticatorMgtDAO; import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtException; import org.wso2.carbon.identity.application.common.model.FederatedAuthenticatorConfig; @@ -43,9 +44,10 @@ */ public class ApplicationAuthenticatorService { + private static final String DISPLAY_NAME = "Display name"; private static volatile ApplicationAuthenticatorService instance; private static final Log LOG = LogFactory.getLog(ApplicationAuthenticatorService.class); - private static final CacheBackedAuthenticatorMgtDAO CACHE_BACKED_DAO = + private static final AuthenticatorManagementDAO dao = new CacheBackedAuthenticatorMgtDAO(new AuthenticatorManagementDAOImpl()); private List localAuthenticators = new ArrayList<>(); @@ -77,7 +79,7 @@ public List getLocalAuthenticators() { public List getAllUserDefinedLocalAuthenticators(String tenantDomain) throws AuthenticatorMgtException { - return CACHE_BACKED_DAO.getAllUserDefinedLocalAuthenticators(IdentityTenantUtil.getTenantId(tenantDomain)); + return dao.getAllUserDefinedLocalAuthenticators(IdentityTenantUtil.getTenantId(tenantDomain)); } public List getFederatedAuthenticators() { @@ -146,6 +148,11 @@ public RequestPathAuthenticatorConfig getRequestPathAuthenticatorByName(String n return null; } + /** + * Add a system defined Local Application Authenticator configuration. + * + * @param authenticator The Local Application Authenticator configuration. + */ public void addLocalAuthenticator(LocalAuthenticatorConfig authenticator) { if (authenticator != null) { @@ -205,10 +212,10 @@ public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( authenticatorConfig.getName()); } authenticatorValidator.validateAuthenticatorName(authenticatorConfig.getName()); - authenticatorValidator.validateForBlank("Display name", authenticatorConfig.getDisplayName()); + authenticatorValidator.validateForBlank(DISPLAY_NAME, authenticatorConfig.getDisplayName()); authenticatorValidator.validateDefinedByType(authenticatorConfig.getDefinedByType()); - return CACHE_BACKED_DAO.addUserDefinedLocalAuthenticator( + return dao.addUserDefinedLocalAuthenticator( authenticatorConfig, IdentityTenantUtil.getTenantId(tenantDomain)); } @@ -227,9 +234,9 @@ public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator( UserDefinedLocalAuthenticatorConfig existingConfig = resolveExistingAuthenticator( authenticatorConfig.getName(), tenantDomain); authenticatorValidator.validateDefinedByType(existingConfig.getDefinedByType()); - authenticatorValidator.validateForBlank("Display name", authenticatorConfig.getDisplayName()); + authenticatorValidator.validateForBlank(DISPLAY_NAME, authenticatorConfig.getDisplayName()); - return CACHE_BACKED_DAO.updateUserDefinedLocalAuthenticator( + return dao.updateUserDefinedLocalAuthenticator( existingConfig, authenticatorConfig, IdentityTenantUtil.getTenantId(tenantDomain)); } @@ -247,7 +254,7 @@ public void deleteUserDefinedLocalAuthenticator(String authenticatorName, String authenticatorName, tenantDomain); authenticatorValidator.validateDefinedByType(existingConfig.getDefinedByType()); - CACHE_BACKED_DAO.deleteUserDefinedLocalAuthenticator(authenticatorName, existingConfig, + dao.deleteUserDefinedLocalAuthenticator(authenticatorName, existingConfig, IdentityTenantUtil.getTenantId(tenantDomain)); } @@ -262,14 +269,14 @@ public void deleteUserDefinedLocalAuthenticator(String authenticatorName, String public UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator(String authenticatorName, String tenantDomain) throws AuthenticatorMgtException { - return CACHE_BACKED_DAO.getUserDefinedLocalAuthenticator( + return dao.getUserDefinedLocalAuthenticator( authenticatorName, IdentityTenantUtil.getTenantId(tenantDomain)); } private UserDefinedLocalAuthenticatorConfig resolveExistingAuthenticator(String authenticatorName, String tenantDomain) throws AuthenticatorMgtException { - UserDefinedLocalAuthenticatorConfig existingAuthenticatorConfig = CACHE_BACKED_DAO. + UserDefinedLocalAuthenticatorConfig existingAuthenticatorConfig = dao. getUserDefinedLocalAuthenticator(authenticatorName, IdentityTenantUtil.getTenantId(tenantDomain)); if (existingAuthenticatorConfig == null) { diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/model/UserDefinedFederatedAuthenticatorConfig.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/model/UserDefinedFederatedAuthenticatorConfig.java index 9bffc4544a34..0397b9182c9d 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/model/UserDefinedFederatedAuthenticatorConfig.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/model/UserDefinedFederatedAuthenticatorConfig.java @@ -27,7 +27,7 @@ public class UserDefinedFederatedAuthenticatorConfig extends FederatedAuthentica private static final String TAG_CUSTOM = "CUSTOM"; - protected UserDefinedAuthenticatorEndpointConfig endpointConfig; + private UserDefinedAuthenticatorEndpointConfig endpointConfig; public UserDefinedFederatedAuthenticatorConfig() { diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/model/UserDefinedLocalAuthenticatorConfig.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/model/UserDefinedLocalAuthenticatorConfig.java index 53f8c68644b2..31dff8247bd8 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/model/UserDefinedLocalAuthenticatorConfig.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/model/UserDefinedLocalAuthenticatorConfig.java @@ -29,8 +29,7 @@ public class UserDefinedLocalAuthenticatorConfig extends LocalAuthenticatorConfi private static final String TAG_2FA = "2FA"; private static final String TAG_CUSTOM = "CUSTOM"; private AuthenticationType authenticationType; - - protected UserDefinedAuthenticatorEndpointConfig endpointConfig; + private UserDefinedAuthenticatorEndpointConfig endpointConfig; public UserDefinedLocalAuthenticatorConfig(AuthenticationType type) { From 980a36bb9f99d2c3a77779f304c6aefd85709023 Mon Sep 17 00:00:00 2001 From: Thisara-Welmilla Date: Wed, 11 Dec 2024 10:58:52 +0530 Subject: [PATCH 05/15] Improve to use cross component transaction. --- .../ApplicationAuthenticatorService.java | 2 +- .../impl/AuthenticatorManagementDAOImpl.java | 246 ++++++++---------- .../impl/AuthenticatorManagementFacade.java | 88 +++++-- .../ApplicationCommonServiceComponent.java | 2 +- .../ApplicationCommonServiceDataHolder.java | 2 +- .../AuthenticatorMgtExceptionBuilder.java | 4 +- .../util/IdentityApplicationConstants.java | 2 + ...nedAuthenticatorEndpointConfigManager.java | 3 +- .../ApplicationAuthenticatorServiceTest.java | 2 +- 9 files changed, 185 insertions(+), 166 deletions(-) diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java index 1ed6e7001f3a..68574cc78645 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java @@ -20,8 +20,8 @@ import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; -import org.wso2.carbon.identity.application.common.dao.impl.AuthenticatorManagementDAOImpl; import org.wso2.carbon.identity.application.common.dao.AuthenticatorManagementDAO; +import org.wso2.carbon.identity.application.common.dao.impl.AuthenticatorManagementDAOImpl; import org.wso2.carbon.identity.application.common.dao.impl.CacheBackedAuthenticatorMgtDAO; import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtException; import org.wso2.carbon.identity.application.common.model.FederatedAuthenticatorConfig; diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java index 89f75b53fcd5..97c6704cc61a 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java @@ -20,7 +20,10 @@ import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; +import org.wso2.carbon.database.utils.jdbc.NamedJdbcTemplate; import org.wso2.carbon.database.utils.jdbc.NamedPreparedStatement; +import org.wso2.carbon.database.utils.jdbc.exceptions.DataAccessException; +import org.wso2.carbon.database.utils.jdbc.exceptions.TransactionException; import org.wso2.carbon.identity.application.common.constant.AuthenticatorMgtSQLConstants.Column; import org.wso2.carbon.identity.application.common.constant.AuthenticatorMgtSQLConstants.Query; import org.wso2.carbon.identity.application.common.dao.AuthenticatorManagementDAO; @@ -41,6 +44,7 @@ import java.util.List; import static org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.buildServerException; +import static org.wso2.carbon.identity.application.common.util.IdentityApplicationConstants.Authenticator.ACTION_ID_PROPERTY; /** * This class implements the AuthenticatorManagementDAO interface which perform CRUD operation on database. @@ -56,38 +60,32 @@ public class AuthenticatorManagementDAOImpl implements AuthenticatorManagementDA public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( UserDefinedLocalAuthenticatorConfig authenticatorConfig, int tenantId) throws AuthenticatorMgtException { - Connection dbConnection = IdentityDatabaseUtil.getDBConnection(true); - - try (NamedPreparedStatement statement = new NamedPreparedStatement(dbConnection, Query.ADD_AUTHENTICATOR_SQL)) { - statement.setString(Column.NAME, authenticatorConfig.getName()); - statement.setString(Column.DISPLAY_NAME, authenticatorConfig.getDisplayName()); - statement.setString(Column.DEFINED_BY, authenticatorConfig.getDefinedByType().toString()); - statement.setString(Column.AUTHENTICATION_TYPE, authenticatorConfig.getAuthenticationType().toString()); - statement.setInt(Column.IS_ENABLED, authenticatorConfig.isEnabled() ? 1 : 0); - statement.setString(Column.IDP_NAME, LOCAL_IDP_NAME); - statement.setInt(Column.TENANT_ID, tenantId); - statement.executeUpdate(); - - if (authenticatorConfig.getProperties() != null) { + NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); + try { + jdbcTemplate.executeInsert(Query.ADD_AUTHENTICATOR_SQL, + (statement -> { + statement.setString(Column.NAME, authenticatorConfig.getName()); + statement.setString(Column.DISPLAY_NAME, authenticatorConfig.getDisplayName()); + statement.setString(Column.DEFINED_BY, authenticatorConfig.getDefinedByType().toString()); + statement.setString(Column.AUTHENTICATION_TYPE, authenticatorConfig.getAuthenticationType() + .toString()); + statement.setInt(Column.IS_ENABLED, authenticatorConfig.isEnabled() ? 1 : 0); + statement.setString(Column.IDP_NAME, LOCAL_IDP_NAME); + statement.setInt(Column.TENANT_ID, tenantId); + }), null, false); - int authenticatorConfigID = getAuthenticatorIdentifier(dbConnection, authenticatorConfig.getName(), - tenantId); - addAuthenticatorProperties(dbConnection, authenticatorConfigID, authenticatorConfig.getProperties(), - tenantId); - } - IdentityDatabaseUtil.commitTransaction(dbConnection); + int authenticatorConfigID = getAuthenticatorIdentifier(authenticatorConfig.getName(), tenantId); + addAuthenticatorProperties(authenticatorConfig.getName(), authenticatorConfigID, + authenticatorConfig.getProperties(), tenantId); - return getUserDefinedLocalAuthenticatorByName(dbConnection, authenticatorConfig.getName(), tenantId); - } catch (SQLException e) { + return getUserDefinedLocalAuthenticatorByName(authenticatorConfig.getName(), tenantId); + } catch (DataAccessException e) { if (LOG.isDebugEnabled()) { LOG.debug(String.format("Error while adding the authenticator: %s in tenant domain: %s. " + "Rolling back added Authenticator information.", authenticatorConfig.getName(), IdentityTenantUtil.getTenantDomain(tenantId))); } - IdentityDatabaseUtil.rollbackTransaction(dbConnection); throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_ADDING_AUTHENTICATOR, e); - } finally { - IdentityDatabaseUtil.closeConnection(dbConnection); } } @@ -97,39 +95,25 @@ public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator( UserDefinedLocalAuthenticatorConfig updatedAuthenticatorConfig, int tenantId) throws AuthenticatorMgtException { - Connection dbConnection = IdentityDatabaseUtil.getDBConnection(true); + NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); try { - if (isBasicInfoUpdated(existingAuthenticatorConfig, updatedAuthenticatorConfig)) { - try (NamedPreparedStatement statement = new NamedPreparedStatement(dbConnection, - Query.UPDATE_AUTHENTICATOR_SQL)) { + jdbcTemplate.executeUpdate(Query.UPDATE_AUTHENTICATOR_SQL, + statement -> { statement.setString(Column.DISPLAY_NAME, updatedAuthenticatorConfig.getDisplayName()); statement.setInt(Column.IS_ENABLED, updatedAuthenticatorConfig.isEnabled() ? 1 : 0); statement.setString(Column.NAME, existingAuthenticatorConfig.getName()); statement.setInt(Column.TENANT_ID, tenantId); statement.executeUpdate(); - } - } + }); - // Will delete all the properties of given authenticator and add the updated properties. - int authenticatorConfigID = getAuthenticatorIdentifier(dbConnection, - existingAuthenticatorConfig.getName(), tenantId); - deletedAuthenticatorProperties(dbConnection, authenticatorConfigID, tenantId); - addAuthenticatorProperties(dbConnection, authenticatorConfigID, updatedAuthenticatorConfig.getProperties(), - tenantId); - - IdentityDatabaseUtil.commitTransaction(dbConnection); - - return getUserDefinedLocalAuthenticatorByName(dbConnection, updatedAuthenticatorConfig.getName(), tenantId); - } catch (SQLException e) { + return getUserDefinedLocalAuthenticatorByName(updatedAuthenticatorConfig.getName(), tenantId); + } catch (DataAccessException e) { if (LOG.isDebugEnabled()) { LOG.debug(String.format("Error while updating the authenticator: %s in tenant domain: %s. " + "Rolling back updated Authenticator information.", existingAuthenticatorConfig.getName(), IdentityTenantUtil.getTenantDomain(tenantId))); } - IdentityDatabaseUtil.rollbackTransaction(dbConnection); throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_UPDATING_AUTHENTICATOR, e); - } finally { - IdentityDatabaseUtil.closeConnection(dbConnection); } } @@ -139,7 +123,9 @@ public UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator( Connection dbConnection = IdentityDatabaseUtil.getDBConnection(false); try { - return getUserDefinedLocalAuthenticatorByName(dbConnection, authenticatorConfigName, tenantId); + return getUserDefinedLocalAuthenticatorByName(authenticatorConfigName, tenantId); + } catch (DataAccessException e) { + throw new RuntimeException(e); } finally { IdentityDatabaseUtil.closeConnection(dbConnection); } @@ -165,7 +151,7 @@ public List getAllUserDefinedLocalAuthentic config.setEnabled(rs.getString(Column.IS_ENABLED).equals(IS_TRUE_VALUE)); config.setDefinedByType(DefinedByType.valueOf(rs.getString(Column.DEFINED_BY))); - int authenticatorConfigID = getAuthenticatorIdentifier(dbConnection, config.getName(), tenantId); + int authenticatorConfigID = getAuthenticatorIdentifier(config.getName(), tenantId); try (NamedPreparedStatement statementProp = new NamedPreparedStatement(dbConnection, Query.GET_AUTHENTICATOR_PROP_SQL)) { statementProp.setInt(Column.AUTHENTICATOR_ID, authenticatorConfigID); @@ -186,6 +172,8 @@ public List getAllUserDefinedLocalAuthentic allUserDefinedLocalConfigs.add(config); } + } catch (DataAccessException e) { + throw new RuntimeException(e); } return allUserDefinedLocalConfigs; @@ -202,75 +190,68 @@ public List getAllUserDefinedLocalAuthentic public void deleteUserDefinedLocalAuthenticator(String authenticatorConfigName, UserDefinedLocalAuthenticatorConfig authenticatorConfig, int tenantId) throws AuthenticatorMgtException { - Connection dbConnection = IdentityDatabaseUtil.getDBConnection(true); - try (NamedPreparedStatement statement = new NamedPreparedStatement(dbConnection, - Query.DELETE_AUTHENTICATOR_SQL)) { - statement.setString(Column.NAME, authenticatorConfigName); - statement.setInt(Column.TENANT_ID, tenantId); - statement.executeUpdate(); - - IdentityDatabaseUtil.commitTransaction(dbConnection); - } catch (SQLException e) { + NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); + try { + jdbcTemplate.withTransaction(template -> { + return template.executeQuery(Query.DELETE_AUTHENTICATOR_SQL, + (resultSet, rowNumber) -> null, + statement -> { + statement.setString(Column.NAME, authenticatorConfigName); + statement.setInt(Column.TENANT_ID, tenantId); + statement.executeUpdate(); + }); + }); + } catch (TransactionException e) { if (LOG.isDebugEnabled()) { LOG.debug(String.format("Error while deleting the authenticator: %s in tenant domain: %s. " + "Rolling back deleted Authenticator information.", authenticatorConfigName, IdentityTenantUtil.getTenantDomain(tenantId))); } - IdentityDatabaseUtil.rollbackTransaction(dbConnection); throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_DELETING_AUTHENTICATOR, e); - } finally { - IdentityDatabaseUtil.closeConnection(dbConnection); } } - private UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticatorByName( - Connection dbConnection, String authenticatorConfigName, int tenantId) - throws AuthenticatorMgtServerException { - - UserDefinedLocalAuthenticatorConfig config = null; - try (NamedPreparedStatement statement = new NamedPreparedStatement(dbConnection, Query.GET_AUTHENTICATOR_SQL)) { - statement.setString(Column.NAME, authenticatorConfigName); - statement.setInt(Column.TENANT_ID, tenantId); - statement.setString(Column.DEFINED_BY, DefinedByType.USER.toString()); + private UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticatorByName(String authenticatorConfigName, + int tenantId) throws AuthenticatorMgtServerException, DataAccessException { - try (ResultSet rs = statement.executeQuery()) { - if (rs.next()) { - config = getLocalAuthenticatorConfigBasedOnType(rs.getString(Column.AUTHENTICATION_TYPE)); - config.setName(rs.getString(Column.NAME)); - config.setDisplayName(rs.getString(Column.DISPLAY_NAME)); - config.setEnabled(rs.getString(Column.IS_ENABLED).equals(IS_TRUE_VALUE)); + NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); + UserDefinedLocalAuthenticatorConfig authConfig = jdbcTemplate.fetchSingleRecord(Query.GET_AUTHENTICATOR_SQL, + (resultSet, rowNumber) -> { + UserDefinedLocalAuthenticatorConfig config = getLocalAuthenticatorConfigBasedOnType( + resultSet.getString(Column.AUTHENTICATION_TYPE)); + config.setName(resultSet.getString(Column.NAME)); + config.setDisplayName(resultSet.getString(Column.DISPLAY_NAME)); + config.setEnabled(resultSet.getString(Column.IS_ENABLED).equals(IS_TRUE_VALUE)); config.setDefinedByType(DefinedByType.USER); - } - } - - if (config == null) { - return null; - } - - int authenticatorConfigID = getAuthenticatorIdentifier(dbConnection, config.getName(), tenantId); - try (NamedPreparedStatement statementProp = new NamedPreparedStatement(dbConnection, - Query.GET_AUTHENTICATOR_PROP_SQL)) { - statementProp.setInt(Column.AUTHENTICATOR_ID, authenticatorConfigID); - statementProp.setInt(Column.TENANT_ID, tenantId); - - try (ResultSet rs = statementProp.executeQuery()) { - List properties = new ArrayList<>(); - while (rs.next()) { - Property property = new Property(); - property.setName(rs.getString(Column.PROPERTY_KEY)); - property.setValue(rs.getString(Column.PROPERTY_VALUE)); - property.setConfidential(false); - properties.add(property); - } - config.setProperties(properties.toArray(new Property[0])); - } - } + return config; + }, + statement -> { + statement.setString(Column.NAME, authenticatorConfigName); + statement.setInt(Column.TENANT_ID, tenantId); + statement.setString(Column.DEFINED_BY, DefinedByType.USER.toString()); + }); - IdentityDatabaseUtil.commitTransaction(dbConnection); - return config; - } catch (SQLException e) { - throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_RETRIEVING_AUTHENTICATOR_BY_NAME, e); + if (authConfig == null) { + return null; } + + int authenticatorConfigID = getAuthenticatorIdentifier(authenticatorConfigName, tenantId); + List properties = new ArrayList<>(); + jdbcTemplate.fetchSingleRecord(Query.GET_AUTHENTICATOR_PROP_SQL, + (resultSet, rowNumber) -> { + Property property = new Property(); + property.setName(resultSet.getString(Column.PROPERTY_KEY)); + property.setValue(resultSet.getString(Column.PROPERTY_VALUE)); + property.setConfidential(false); + properties.add(property); + return null; + }, + statementProp -> { + statementProp.setInt(Column.AUTHENTICATOR_ID, authenticatorConfigID); + statementProp.setInt(Column.TENANT_ID, tenantId); + }); + authConfig.setProperties(properties.toArray(new Property[0])); + return authConfig; } private UserDefinedLocalAuthenticatorConfig getLocalAuthenticatorConfigBasedOnType(String authenticationType) { @@ -281,48 +262,37 @@ private UserDefinedLocalAuthenticatorConfig getLocalAuthenticatorConfigBasedOnTy return new UserDefinedLocalAuthenticatorConfig(AuthenticationType.IDENTIFICATION); } - private boolean isBasicInfoUpdated(UserDefinedLocalAuthenticatorConfig existingAuthenticatorConfig, - UserDefinedLocalAuthenticatorConfig updatedAuthenticatorConfig) { - - return !existingAuthenticatorConfig.getDisplayName().equals(updatedAuthenticatorConfig.getDisplayName()) || - existingAuthenticatorConfig.isEnabled() != updatedAuthenticatorConfig.isEnabled(); - } + private int getAuthenticatorIdentifier(String authenticatorConfigName, int tenantId) + throws AuthenticatorMgtServerException, DataAccessException { - private int getAuthenticatorIdentifier(Connection dbConnection, String authenticatorConfigName, - int tenantId) throws AuthenticatorMgtServerException, SQLException { + NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); + String id = jdbcTemplate.fetchSingleRecord(Query.GET_AUTHENTICATOR_ID_SQL, + (resultSet, rowNumber) -> resultSet.getString(Column.ID), + statement -> { + statement.setString(Column.NAME, authenticatorConfigName); + statement.setInt(Column.TENANT_ID, tenantId); + }); - try (NamedPreparedStatement statement = new NamedPreparedStatement(dbConnection, - Query.GET_AUTHENTICATOR_ID_SQL)) { - statement.setString(Column.NAME, authenticatorConfigName); - statement.setInt(Column.TENANT_ID, tenantId); - - try (ResultSet rs = statement.executeQuery()) { - if (rs.next()) { - return rs.getInt(Column.ID); - } - } - IdentityDatabaseUtil.commitTransaction(dbConnection); + if (id != null) { + return Integer.parseInt(id); } - throw buildServerException(AuthenticatorMgtError.ERROR_CODE_NO_AUTHENTICATOR_FOUND, authenticatorConfigName); + throw buildServerException(AuthenticatorMgtError.ERROR_CODE_NO_AUTHENTICATOR_FOUND, + authenticatorConfigName); } - private void deletedAuthenticatorProperties(Connection dbConnection, int authenticatorConfigID, int tenantId) - throws SQLException { + private void addAuthenticatorProperties(String authenticatorName, + int authenticatorConfigID, Property[] properties, int tenantId) + throws DataAccessException, AuthenticatorMgtServerException { - try (NamedPreparedStatement statementDeleteProp = new NamedPreparedStatement(dbConnection, - Query.DELETE_AUTHENTICATOR_PROP_SQL)) { - statementDeleteProp.setInt(Column.AUTHENTICATOR_ID, authenticatorConfigID); - statementDeleteProp.setInt(Column.TENANT_ID, tenantId); - statementDeleteProp.executeUpdate(); + if (!(properties.length == 1 && ACTION_ID_PROPERTY.equals(properties[0].getName()))) { + throw buildServerException(AuthenticatorMgtError.ERROR_CODE_HAVING_MULTIPLE_PROP, + properties[0].getName()); } - } - private void addAuthenticatorProperties(Connection dbConnection, int authenticatorConfigID, Property[] properties, - int tenantId) throws SQLException { - - try (NamedPreparedStatement statementProp = new NamedPreparedStatement(dbConnection, - Query.ADD_AUTHENTICATOR_PROP_SQL)) { - for (Property prop : properties) { + Property prop = properties[0]; + NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); + jdbcTemplate.executeInsert(Query.ADD_AUTHENTICATOR_PROP_SQL, + (statementProp -> { statementProp.setInt(Column.AUTHENTICATOR_ID, authenticatorConfigID); statementProp.setInt(Column.TENANT_ID, tenantId); statementProp.setString(Column.PROPERTY_KEY, prop.getName()); @@ -332,8 +302,6 @@ private void addAuthenticatorProperties(Connection dbConnection, int authenticat } else { statementProp.setString(Column.IS_SECRET, IS_FALSE_VALUE); } - statementProp.executeUpdate(); - } - } + }), null, false); } } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java index 2e086b8eafb6..8f6378eb0a96 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java @@ -18,10 +18,18 @@ package org.wso2.carbon.identity.application.common.dao.impl; +import org.apache.commons.logging.Log; +import org.apache.commons.logging.LogFactory; +import org.wso2.carbon.database.utils.jdbc.NamedJdbcTemplate; +import org.wso2.carbon.database.utils.jdbc.exceptions.TransactionException; import org.wso2.carbon.identity.application.common.dao.AuthenticatorManagementDAO; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtClientException; import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtException; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtServerException; import org.wso2.carbon.identity.application.common.model.UserDefinedLocalAuthenticatorConfig; import org.wso2.carbon.identity.application.common.util.UserDefinedAuthenticatorEndpointConfigManager; +import org.wso2.carbon.identity.core.util.IdentityDatabaseUtil; +import org.wso2.carbon.identity.core.util.IdentityTenantUtil; import java.util.List; @@ -31,6 +39,8 @@ */ public class AuthenticatorManagementFacade implements AuthenticatorManagementDAO { + private static final Log LOG = LogFactory.getLog(AuthenticatorManagementFacade.class); + private final AuthenticatorManagementDAO dao; private UserDefinedAuthenticatorEndpointConfigManager endpointConfigManager = new UserDefinedAuthenticatorEndpointConfigManager(); @@ -44,13 +54,20 @@ public AuthenticatorManagementFacade(AuthenticatorManagementDAO dao) { public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( UserDefinedLocalAuthenticatorConfig authenticatorConfig, int tenantId) throws AuthenticatorMgtException { - endpointConfigManager.addEndpointConfigurations(authenticatorConfig, tenantId); + + NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); try { - return endpointConfigManager.resolveEndpointConfigurations( - dao.addUserDefinedLocalAuthenticator(authenticatorConfig, tenantId), tenantId); - } catch (AuthenticatorMgtException e) { - endpointConfigManager.deleteEndpointConfigurations(authenticatorConfig, tenantId); - throw e; + return jdbcTemplate.withTransaction(template -> { + endpointConfigManager.addEndpointConfigurations(authenticatorConfig, tenantId); + return endpointConfigManager.resolveEndpointConfigurations( + dao.addUserDefinedLocalAuthenticator(authenticatorConfig, tenantId), tenantId); + }); + } catch (TransactionException e) { + // Since exceptions thrown are wrapped with TransactionException, extracting the actual cause. + LOG.debug("Error while creating the user defined local authenticator: " + authenticatorConfig.getName() + + " in Tenant Domain: " + IdentityTenantUtil.getTenantDomain(tenantId) + + ". Rolling back created authenticator information, and associated action."); + throw handleAuthenticatorMgtException(e); } } @@ -59,16 +76,22 @@ public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator(U existingAuthenticatorConfig, UserDefinedLocalAuthenticatorConfig newAuthenticatorConfig, int tenantId) throws AuthenticatorMgtException { - endpointConfigManager.updateEndpointConfigurations(newAuthenticatorConfig, existingAuthenticatorConfig, - tenantId); + NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); try { - return endpointConfigManager.resolveEndpointConfigurations( - dao.updateUserDefinedLocalAuthenticator(existingAuthenticatorConfig, newAuthenticatorConfig, - tenantId), tenantId); - } catch (AuthenticatorMgtException e) { - endpointConfigManager.updateEndpointConfigurations(existingAuthenticatorConfig, newAuthenticatorConfig, - tenantId); - throw e; + return jdbcTemplate.withTransaction(template -> { + endpointConfigManager.updateEndpointConfigurations(newAuthenticatorConfig, existingAuthenticatorConfig, + tenantId); + return endpointConfigManager.resolveEndpointConfigurations( + dao.updateUserDefinedLocalAuthenticator(existingAuthenticatorConfig, newAuthenticatorConfig, + tenantId), tenantId); + }); + } catch (TransactionException e) { + // Since exceptions thrown are wrapped with TransactionException, extracting the actual cause. + LOG.debug("Error while updating the user defined local authenticator: " + + newAuthenticatorConfig.getName() + " in Tenant Domain: " + + IdentityTenantUtil.getTenantDomain(tenantId) + + ". Rolling back updated authenticator information, and associated action."); + throw handleAuthenticatorMgtException(e); } } @@ -96,12 +119,37 @@ public List getAllUserDefinedLocalAuthentic public void deleteUserDefinedLocalAuthenticator(String authenticatorConfigName, UserDefinedLocalAuthenticatorConfig authenticatorConfig, int tenantId) throws AuthenticatorMgtException { - endpointConfigManager.deleteEndpointConfigurations(authenticatorConfig, tenantId); + NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); try { - dao.deleteUserDefinedLocalAuthenticator(authenticatorConfigName, authenticatorConfig, tenantId); - } catch (AuthenticatorMgtException e) { - endpointConfigManager.addEndpointConfigurations(authenticatorConfig, tenantId); - throw e; + jdbcTemplate.withTransaction(template -> { + endpointConfigManager.deleteEndpointConfigurations(authenticatorConfig, tenantId); + dao.deleteUserDefinedLocalAuthenticator(authenticatorConfigName, authenticatorConfig, tenantId); + return null; + }); + } catch (TransactionException e) { + // Since exceptions thrown are wrapped with TransactionException, extracting the actual cause. + LOG.debug("Error while deleting the user defined local authenticator: " + authenticatorConfigName + + " in Tenant Domain: " + IdentityTenantUtil.getTenantDomain(tenantId) + + ". Rolling back deleted authenticator information, and associated action."); + throw handleAuthenticatorMgtException(e); } } + + /** + * Handle the authenticator management client exception. + * + * @param throwable Throwable object. + * @throws AuthenticatorMgtClientException If an authenticator management client exception. + */ + private static AuthenticatorMgtException handleAuthenticatorMgtException(Throwable throwable) + throws AuthenticatorMgtException { + + if (throwable instanceof AuthenticatorMgtClientException) { + AuthenticatorMgtClientException error = (AuthenticatorMgtClientException) throwable; + throw new AuthenticatorMgtClientException(error.getErrorCode(), error.getMessage(), error.getDescription()); + } + + AuthenticatorMgtServerException error = (AuthenticatorMgtServerException) throwable; + throw new AuthenticatorMgtServerException(error.getErrorCode(), error.getMessage(), error.getDescription()); + } } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/internal/ApplicationCommonServiceComponent.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/internal/ApplicationCommonServiceComponent.java index c5c3e818aa3e..7277f69d2054 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/internal/ApplicationCommonServiceComponent.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/internal/ApplicationCommonServiceComponent.java @@ -9,7 +9,7 @@ import org.osgi.service.component.annotations.Reference; import org.osgi.service.component.annotations.ReferenceCardinality; import org.osgi.service.component.annotations.ReferencePolicy; -import org.wso2.carbon.identity.action.management.ActionManagementService; +import org.wso2.carbon.identity.action.management.service.ActionManagementService; import org.wso2.carbon.identity.application.common.ApplicationAuthenticatorService; /** diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/internal/ApplicationCommonServiceDataHolder.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/internal/ApplicationCommonServiceDataHolder.java index 7c333500324a..238b81ebcf35 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/internal/ApplicationCommonServiceDataHolder.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/internal/ApplicationCommonServiceDataHolder.java @@ -1,6 +1,6 @@ package org.wso2.carbon.identity.application.common.internal; -import org.wso2.carbon.identity.action.management.ActionManagementService; +import org.wso2.carbon.identity.action.management.service.ActionManagementService; import org.wso2.carbon.identity.application.common.ApplicationAuthenticatorService; /** diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/AuthenticatorMgtExceptionBuilder.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/AuthenticatorMgtExceptionBuilder.java index e52cddb4baed..2af2b74f3d81 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/AuthenticatorMgtExceptionBuilder.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/AuthenticatorMgtExceptionBuilder.java @@ -113,7 +113,9 @@ public enum AuthenticatorMgtError { ERROR_CODE_RETRIEVING_ENDPOINT_CONFIG("65010", "Error while resolving endpoint configurations.", "Error while retrieving endpoint configurations for the user defined local authenticator %s."), ERROR_CODE_DELETING_ENDPOINT_CONFIG("65011", "Error while managing endpoint configurations.", - "Error while managing endpoint configurations for the user defined local authenticator %s."); + "Error while managing endpoint configurations for the user defined local authenticator %s."), + ERROR_CODE_HAVING_MULTIPLE_PROP("65012", "Multiple properties found", "Only actionId " + + "property is allowed for authenticator: %s."); private final String code; private final String message; diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/IdentityApplicationConstants.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/IdentityApplicationConstants.java index 1c748599ab6c..8bdbfc112044 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/IdentityApplicationConstants.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/IdentityApplicationConstants.java @@ -166,6 +166,8 @@ private ConfigElements() { */ public static class Authenticator { + public static final String ACTION_ID_PROPERTY = "actionId"; + /** * OpenId authenticator constants. */ diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedAuthenticatorEndpointConfigManager.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedAuthenticatorEndpointConfigManager.java index 12fb7dbe7006..04fa9447c718 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedAuthenticatorEndpointConfigManager.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedAuthenticatorEndpointConfigManager.java @@ -34,6 +34,7 @@ import java.util.Map; import static org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.buildServerException; +import static org.wso2.carbon.identity.application.common.util.IdentityApplicationConstants.Authenticator.ACTION_ID_PROPERTY; /** * This class responsible for managing authenticator endpoint configurations for the user defined Local @@ -41,8 +42,6 @@ */ public class UserDefinedAuthenticatorEndpointConfigManager { - private static final String ACTION_ID_PROPERTY = "actionId"; - /** * Create a new action for given endpoint configurations of the user defined authenticator. * diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java index b54d245727ef..f4931b22c168 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java @@ -24,11 +24,11 @@ import org.testng.annotations.BeforeClass; import org.testng.annotations.DataProvider; import org.testng.annotations.Test; -import org.wso2.carbon.identity.action.management.ActionManagementService; import org.wso2.carbon.identity.action.management.exception.ActionMgtException; import org.wso2.carbon.identity.action.management.model.Action; import org.wso2.carbon.identity.action.management.model.Authentication; import org.wso2.carbon.identity.action.management.model.EndpointConfig; +import org.wso2.carbon.identity.action.management.service.ActionManagementService; import org.wso2.carbon.identity.application.common.ApplicationAuthenticatorService; import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtException; import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtServerRuntimeException; From 1191c5b63906755e61887328ebc03a551136335b Mon Sep 17 00:00:00 2001 From: Thisara-Welmilla Date: Wed, 11 Dec 2024 12:10:12 +0530 Subject: [PATCH 06/15] Address comments. --- .../ApplicationAuthenticatorService.java | 15 ++++++++------- .../impl/AuthenticatorManagementDAOImpl.java | 19 ++++++++----------- .../impl/AuthenticatorManagementFacade.java | 6 +++--- .../exception/AuthenticatorMgtException.java | 15 ++------------- ...serDefinedLocalAuthenticatorValidator.java | 15 --------------- .../ApplicationAuthenticatorServiceTest.java | 3 +-- 6 files changed, 22 insertions(+), 51 deletions(-) diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java index 68574cc78645..2b6121188476 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java @@ -213,7 +213,6 @@ public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( } authenticatorValidator.validateAuthenticatorName(authenticatorConfig.getName()); authenticatorValidator.validateForBlank(DISPLAY_NAME, authenticatorConfig.getDisplayName()); - authenticatorValidator.validateDefinedByType(authenticatorConfig.getDefinedByType()); return dao.addUserDefinedLocalAuthenticator( authenticatorConfig, IdentityTenantUtil.getTenantId(tenantDomain)); @@ -233,7 +232,11 @@ public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator( UserDefinedLocalAuthenticatorConfig existingConfig = resolveExistingAuthenticator( authenticatorConfig.getName(), tenantDomain); - authenticatorValidator.validateDefinedByType(existingConfig.getDefinedByType()); + if (existingConfig == null) { + throw buildClientException(AuthenticatorMgtError.ERROR_NOT_FOUND_AUTHENTICATOR, + authenticatorConfig.getName()); + } + authenticatorValidator.validateForBlank(DISPLAY_NAME, authenticatorConfig.getDisplayName()); return dao.updateUserDefinedLocalAuthenticator( @@ -252,7 +255,9 @@ public void deleteUserDefinedLocalAuthenticator(String authenticatorName, String UserDefinedLocalAuthenticatorConfig existingConfig = resolveExistingAuthenticator( authenticatorName, tenantDomain); - authenticatorValidator.validateDefinedByType(existingConfig.getDefinedByType()); + if (existingConfig == null) { + return; + } dao.deleteUserDefinedLocalAuthenticator(authenticatorName, existingConfig, IdentityTenantUtil.getTenantId(tenantDomain)); @@ -279,10 +284,6 @@ private UserDefinedLocalAuthenticatorConfig resolveExistingAuthenticator(String UserDefinedLocalAuthenticatorConfig existingAuthenticatorConfig = dao. getUserDefinedLocalAuthenticator(authenticatorName, IdentityTenantUtil.getTenantId(tenantDomain)); - if (existingAuthenticatorConfig == null) { - throw buildClientException(AuthenticatorMgtError.ERROR_NOT_FOUND_AUTHENTICATOR, authenticatorName); - } - return existingAuthenticatorConfig; } } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java index 97c6704cc61a..3d459eaec35e 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java @@ -23,7 +23,6 @@ import org.wso2.carbon.database.utils.jdbc.NamedJdbcTemplate; import org.wso2.carbon.database.utils.jdbc.NamedPreparedStatement; import org.wso2.carbon.database.utils.jdbc.exceptions.DataAccessException; -import org.wso2.carbon.database.utils.jdbc.exceptions.TransactionException; import org.wso2.carbon.identity.application.common.constant.AuthenticatorMgtSQLConstants.Column; import org.wso2.carbon.identity.application.common.constant.AuthenticatorMgtSQLConstants.Query; import org.wso2.carbon.identity.application.common.dao.AuthenticatorManagementDAO; @@ -192,16 +191,14 @@ public void deleteUserDefinedLocalAuthenticator(String authenticatorConfigName, NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); try { - jdbcTemplate.withTransaction(template -> { - return template.executeQuery(Query.DELETE_AUTHENTICATOR_SQL, - (resultSet, rowNumber) -> null, - statement -> { - statement.setString(Column.NAME, authenticatorConfigName); - statement.setInt(Column.TENANT_ID, tenantId); - statement.executeUpdate(); - }); - }); - } catch (TransactionException e) { + + jdbcTemplate.executeUpdate(Query.DELETE_AUTHENTICATOR_SQL, + statement -> { + statement.setString(Column.NAME, authenticatorConfigName); + statement.setInt(Column.TENANT_ID, tenantId); + statement.executeUpdate(); + }); + } catch (DataAccessException e) { if (LOG.isDebugEnabled()) { LOG.debug(String.format("Error while deleting the authenticator: %s in tenant domain: %s. " + "Rolling back deleted Authenticator information.", authenticatorConfigName, diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java index 8f6378eb0a96..f9f885557e1a 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java @@ -67,7 +67,7 @@ public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( LOG.debug("Error while creating the user defined local authenticator: " + authenticatorConfig.getName() + " in Tenant Domain: " + IdentityTenantUtil.getTenantDomain(tenantId) + ". Rolling back created authenticator information, and associated action."); - throw handleAuthenticatorMgtException(e); + throw handleAuthenticatorMgtException(e.getCause()); } } @@ -91,7 +91,7 @@ public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator(U newAuthenticatorConfig.getName() + " in Tenant Domain: " + IdentityTenantUtil.getTenantDomain(tenantId) + ". Rolling back updated authenticator information, and associated action."); - throw handleAuthenticatorMgtException(e); + throw handleAuthenticatorMgtException(e.getCause()); } } @@ -131,7 +131,7 @@ public void deleteUserDefinedLocalAuthenticator(String authenticatorConfigName, LOG.debug("Error while deleting the user defined local authenticator: " + authenticatorConfigName + " in Tenant Domain: " + IdentityTenantUtil.getTenantDomain(tenantId) + ". Rolling back deleted authenticator information, and associated action."); - throw handleAuthenticatorMgtException(e); + throw handleAuthenticatorMgtException(e.getCause()); } } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtException.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtException.java index 1e2e37da3981..1ba49c6214de 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtException.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtException.java @@ -23,19 +23,8 @@ */ public class AuthenticatorMgtException extends Exception { - private String errorCode; - private String description; - - public AuthenticatorMgtException(String message) { - - super(message); - } - - public AuthenticatorMgtException(String message, String errorCode, Throwable cause) { - - super(message, cause); - this.errorCode = errorCode; - } + private final String errorCode; + private final String description; public AuthenticatorMgtException(String message, String description, String errorCode) { diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedLocalAuthenticatorValidator.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedLocalAuthenticatorValidator.java index a457c1d49f91..836607835390 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedLocalAuthenticatorValidator.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedLocalAuthenticatorValidator.java @@ -21,7 +21,6 @@ import org.apache.commons.lang.StringUtils; import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtClientException; import org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.AuthenticatorMgtError; -import org.wso2.carbon.identity.base.AuthenticatorPropertyConstants.DefinedByType; import java.util.regex.Pattern; @@ -63,18 +62,4 @@ public void validateAuthenticatorName(String name) throws AuthenticatorMgtClient name, AUTHENTICATOR_NAME_REGEX); } } - - /** - * Validate the authenticator is a user defined by authenticator. - * - * @param definedByType The defined by type of the authenticator config. - * @throws AuthenticatorMgtClientException if the authenticator is not a user defined authenticator. - */ - public void validateDefinedByType(DefinedByType definedByType) - throws AuthenticatorMgtClientException { - - if (definedByType != DefinedByType.USER) { - throw buildClientException(AuthenticatorMgtError.ERROR_OP_ON_SYSTEM_AUTHENTICATOR); - } - } } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java index f4931b22c168..2aa81ce8a8db 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java @@ -353,8 +353,7 @@ public void testDeleteUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticato .getLocalAuthenticatorByName(config.getName())); } - @Test(priority = 51, expectedExceptions = AuthenticatorMgtException.class, - expectedExceptionsMessageRegExp = "No Authenticator found.") + @Test(priority = 51) public void testDeleteUserDefinedLocalAuthenticatorWithNonExistingAuthenticator() throws AuthenticatorMgtException { ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() From 1f9d94d8a60b8395c982ac41d59b2cace0c7c5e3 Mon Sep 17 00:00:00 2001 From: Thisara-Welmilla Date: Wed, 11 Dec 2024 17:29:47 +0530 Subject: [PATCH 07/15] Improve unit tests. --- .../ApplicationAuthenticatorService.java | 5 +- .../impl/AuthenticatorManagementDAOImpl.java | 20 +- ...uthenticatorMgtServerRuntimeException.java | 5 - .../ApplicationAuthenticatorServiceTest.java | 84 ++------- .../AuthenticatorManagementDAOImplTest.java | 176 ++++++++++++++++++ .../model/test/util/ActionMgtTestUtil.java | 55 ++---- ...UserDefinedLocalAuthenticatorDataUtil.java | 164 ++++++++++++++++ .../src/test/resources/testng.xml | 3 +- 8 files changed, 386 insertions(+), 126 deletions(-) create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/dao/AuthenticatorManagementDAOImplTest.java create mode 100644 components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/util/UserDefinedLocalAuthenticatorDataUtil.java diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java index 2b6121188476..4178341b9954 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java @@ -281,9 +281,6 @@ public UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator(Stri private UserDefinedLocalAuthenticatorConfig resolveExistingAuthenticator(String authenticatorName, String tenantDomain) throws AuthenticatorMgtException { - UserDefinedLocalAuthenticatorConfig existingAuthenticatorConfig = dao. - getUserDefinedLocalAuthenticator(authenticatorName, IdentityTenantUtil.getTenantId(tenantDomain)); - - return existingAuthenticatorConfig; + return dao.getUserDefinedLocalAuthenticator(authenticatorName, IdentityTenantUtil.getTenantId(tenantDomain)); } } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java index 3d459eaec35e..bdb532e39a6c 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java @@ -124,7 +124,11 @@ public UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator( try { return getUserDefinedLocalAuthenticatorByName(authenticatorConfigName, tenantId); } catch (DataAccessException e) { - throw new RuntimeException(e); + if (LOG.isDebugEnabled()) { + LOG.debug(String.format("Error while retrieving the user defined local authenticator:%s in tenant " + + "domain: %s.", authenticatorConfigName, IdentityTenantUtil.getTenantDomain(tenantId))); + } + throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_RETRIEVING_AUTHENTICATOR_BY_NAME, e); } finally { IdentityDatabaseUtil.closeConnection(dbConnection); } @@ -171,17 +175,14 @@ public List getAllUserDefinedLocalAuthentic allUserDefinedLocalConfigs.add(config); } - } catch (DataAccessException e) { - throw new RuntimeException(e); } - return allUserDefinedLocalConfigs; - } catch (SQLException e) { + } catch (SQLException | DataAccessException e) { if (LOG.isDebugEnabled()) { LOG.debug(String.format("Error while retrieving the all user defined local authenticators in tenant " + "domain: %s.", IdentityTenantUtil.getTenantDomain(tenantId))); } - throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_DELETING_AUTHENTICATOR, e); + throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_RETRIEVING_AUTHENTICATOR_BY_NAME, e); } } @@ -277,13 +278,12 @@ private int getAuthenticatorIdentifier(String authenticatorConfigName, int tenan authenticatorConfigName); } - private void addAuthenticatorProperties(String authenticatorName, - int authenticatorConfigID, Property[] properties, int tenantId) - throws DataAccessException, AuthenticatorMgtServerException { + private void addAuthenticatorProperties(String authenticatorName, int authenticatorConfigID, Property[] properties, + int tenantId) throws DataAccessException, AuthenticatorMgtServerException { if (!(properties.length == 1 && ACTION_ID_PROPERTY.equals(properties[0].getName()))) { throw buildServerException(AuthenticatorMgtError.ERROR_CODE_HAVING_MULTIPLE_PROP, - properties[0].getName()); + authenticatorName); } Property prop = properties[0]; diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtServerRuntimeException.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtServerRuntimeException.java index 1c4bad60ce9d..3c8d4070f699 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtServerRuntimeException.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/exception/AuthenticatorMgtServerRuntimeException.java @@ -45,9 +45,4 @@ public String getDescription() { return this.description; } - - public Throwable getCause() { - - return this.cause; - } } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java index 2aa81ce8a8db..088697fcadcb 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java @@ -18,15 +18,14 @@ package org.wso2.carbon.identity.application.common.model.test; -import org.mockito.MockedStatic; import org.testng.Assert; +import org.testng.annotations.AfterClass; import org.testng.annotations.AfterMethod; import org.testng.annotations.BeforeClass; import org.testng.annotations.DataProvider; import org.testng.annotations.Test; import org.wso2.carbon.identity.action.management.exception.ActionMgtException; import org.wso2.carbon.identity.action.management.model.Action; -import org.wso2.carbon.identity.action.management.model.Authentication; import org.wso2.carbon.identity.action.management.model.EndpointConfig; import org.wso2.carbon.identity.action.management.service.ActionManagementService; import org.wso2.carbon.identity.application.common.ApplicationAuthenticatorService; @@ -34,8 +33,6 @@ import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtServerRuntimeException; import org.wso2.carbon.identity.application.common.internal.ApplicationCommonServiceDataHolder; import org.wso2.carbon.identity.application.common.model.LocalAuthenticatorConfig; -import org.wso2.carbon.identity.application.common.model.Property; -import org.wso2.carbon.identity.application.common.model.UserDefinedAuthenticatorEndpointConfig.UserDefinedAuthenticatorEndpointConfigBuilder; import org.wso2.carbon.identity.application.common.model.UserDefinedLocalAuthenticatorConfig; import org.wso2.carbon.identity.application.common.model.test.util.ActionMgtTestUtil; import org.wso2.carbon.identity.base.AuthenticatorPropertyConstants.AuthenticationType; @@ -46,19 +43,20 @@ import org.wso2.carbon.identity.common.testng.WithRealmService; import org.wso2.carbon.identity.common.testng.WithRegistry; import org.wso2.carbon.identity.core.internal.IdentityCoreServiceDataHolder; -import org.wso2.carbon.identity.core.util.IdentityDatabaseUtil; import java.util.Arrays; -import java.util.HashMap; import java.util.List; import static org.junit.Assert.assertThrows; import static org.mockito.ArgumentMatchers.any; import static org.mockito.ArgumentMatchers.anyString; -import static org.mockito.Mockito.doNothing; import static org.mockito.Mockito.doThrow; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.when; +import static org.wso2.carbon.identity.application.common.model.test.util.ActionMgtTestUtil.mockActionService; +import static org.wso2.carbon.identity.application.common.model.test.util.UserDefinedLocalAuthenticatorDataUtil.createSystemDefinedAuthenticatorConfig; +import static org.wso2.carbon.identity.application.common.model.test.util.UserDefinedLocalAuthenticatorDataUtil.createUserDefinedAuthenticatorConfig; +import static org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.AuthenticatorMgtError.ERROR_CODE_INVALID_DEFINED_BY_AUTH_PROVIDED; /** * This class is a test suite for the ApplicationAuthenticatorServiceTest class. @@ -72,7 +70,6 @@ @WithRealmService(injectToSingletons = {IdentityCoreServiceDataHolder.class}) public class ApplicationAuthenticatorServiceTest { - private MockedStatic identityDatabaseUtil; private String tenantDomain; private UserDefinedLocalAuthenticatorConfig authenticatorConfig1; @@ -110,18 +107,22 @@ public void setUpClass() throws Exception { endpointConfigToBeUpdated = ActionMgtTestUtil.createEndpointConfig( "http://localhost1", "admin1", "admin1"); action = ActionMgtTestUtil.createAction(endpointConfig); - actionManagementService = mock(ActionManagementService.class); - - when(actionManagementService.addAction(anyString(), any(), any())).thenReturn(action); - when(actionManagementService.updateAction(anyString(), any(), any(), any())).thenReturn(action); - when(actionManagementService.getActionByActionId(anyString(), any(), any())).thenReturn(action); - doNothing().when(actionManagementService).deleteAction(anyString(), any(), any()); + actionManagementService = mockActionService(action); ApplicationCommonServiceDataHolder.getInstance().setApplicationAuthenticatorService( ApplicationAuthenticatorService.getInstance()); ApplicationCommonServiceDataHolder.getInstance().setActionManagementService(actionManagementService); } + @AfterClass + public void tearDownClass() throws AuthenticatorMgtException { + + ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() + .deleteUserDefinedLocalAuthenticator(AUTHENTICATOR1_NAME, tenantDomain); + ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() + .deleteUserDefinedLocalAuthenticator(AUTHENTICATOR2_NAME, tenantDomain); + } + @AfterMethod public void tearDown() { @@ -210,9 +211,11 @@ public void testAddLocalAuthenticator() { @Test(priority = 6) public void testAddLocalAuthenticatorWithRuntimeError() { - assertThrows(AuthenticatorMgtServerRuntimeException.class, () -> - ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() + AuthenticatorMgtServerRuntimeException exception = assertThrows(AuthenticatorMgtServerRuntimeException.class, + () -> ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() .addLocalAuthenticator(authenticatorConfig1)); + Assert.assertEquals(exception.getErrorCode(), ERROR_CODE_INVALID_DEFINED_BY_AUTH_PROVIDED.getCode()); + } @Test(priority = 10) @@ -359,53 +362,4 @@ public void testDeleteUserDefinedLocalAuthenticatorWithNonExistingAuthenticator( ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() .deleteUserDefinedLocalAuthenticator(nonExistAuthenticatorConfig.getName(), tenantDomain); } - - private UserDefinedLocalAuthenticatorConfig createUserDefinedAuthenticatorConfig(String uniqueIdentifier, - AuthenticationType type) { - - UserDefinedLocalAuthenticatorConfig authenticatorConfig = new - UserDefinedLocalAuthenticatorConfig(AuthenticationType.IDENTIFICATION); - authenticatorConfig.setName(uniqueIdentifier); - authenticatorConfig.setDisplayName("Custom " + uniqueIdentifier); - authenticatorConfig.setEnabled(true); - authenticatorConfig.setDefinedByType(DefinedByType.USER); - authenticatorConfig.setAuthenticationType(type); - UserDefinedAuthenticatorEndpointConfigBuilder endpointConfigBuilder = buildAuthenticatorEndpointConfig(); - authenticatorConfig.setEndpointConfig(endpointConfigBuilder.build()); - - return authenticatorConfig; - } - - private LocalAuthenticatorConfig createSystemDefinedAuthenticatorConfig(String uniqueIdentifier) { - - LocalAuthenticatorConfig authenticatorConfig = new LocalAuthenticatorConfig(); - authenticatorConfig.setName(uniqueIdentifier); - authenticatorConfig.setDisplayName("Custom " + uniqueIdentifier); - authenticatorConfig.setEnabled(true); - authenticatorConfig.setDefinedByType(DefinedByType.SYSTEM); - Property prop1 = new Property(); - prop1.setName("PropertyName1_" + uniqueIdentifier); - prop1.setValue("PropertyValue1_" + uniqueIdentifier); - prop1.setConfidential(false); - Property prop2 = new Property(); - prop2.setName("PropertyName2_" + uniqueIdentifier); - prop2.setValue("PropertyValue2_" + uniqueIdentifier); - prop2.setConfidential(true); - authenticatorConfig.setProperties(new Property[]{prop1, prop2}); - - return authenticatorConfig; - } - - private static UserDefinedAuthenticatorEndpointConfigBuilder buildAuthenticatorEndpointConfig() { - - UserDefinedAuthenticatorEndpointConfigBuilder endpointConfigBuilder = - new UserDefinedAuthenticatorEndpointConfigBuilder(); - endpointConfigBuilder.uri("https://localhost:8080/test"); - endpointConfigBuilder.authenticationType(Authentication.Type.BASIC.getName()); - HashMap authProperties = new HashMap<>(); - authProperties.put("username", "admin"); - authProperties.put("password", "admin"); - endpointConfigBuilder.authenticationProperties(authProperties); - return endpointConfigBuilder; - } } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/dao/AuthenticatorManagementDAOImplTest.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/dao/AuthenticatorManagementDAOImplTest.java new file mode 100644 index 000000000000..f2f06a88b27d --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/dao/AuthenticatorManagementDAOImplTest.java @@ -0,0 +1,176 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.model.test.dao; + +import org.testng.Assert; +import org.testng.annotations.BeforeClass; +import org.testng.annotations.DataProvider; +import org.testng.annotations.Test; +import org.wso2.carbon.identity.application.common.dao.impl.AuthenticatorManagementDAOImpl; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtException; +import org.wso2.carbon.identity.application.common.model.Property; +import org.wso2.carbon.identity.application.common.model.UserDefinedLocalAuthenticatorConfig; +import org.wso2.carbon.identity.application.common.model.test.util.UserDefinedLocalAuthenticatorDataUtil; +import org.wso2.carbon.identity.base.AuthenticatorPropertyConstants; +import org.wso2.carbon.identity.common.testng.WithCarbonHome; +import org.wso2.carbon.identity.common.testng.WithH2Database; +import org.wso2.carbon.identity.common.testng.WithRealmService; +import org.wso2.carbon.identity.core.internal.IdentityCoreServiceDataHolder; + +import static org.junit.Assert.assertThrows; +import static org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.AuthenticatorMgtError.ERROR_WHILE_ADDING_AUTHENTICATOR; +import static org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.AuthenticatorMgtError.ERROR_WHILE_UPDATING_AUTHENTICATOR; + +@WithH2Database(files = {"dbscripts/h2.sql"}) +@WithCarbonHome +@WithRealmService(injectToSingletons = {IdentityCoreServiceDataHolder.class}) +public class AuthenticatorManagementDAOImplTest { + + private final int tenantId = -1234; + + private UserDefinedLocalAuthenticatorConfig authenticatorConfig1; + private UserDefinedLocalAuthenticatorConfig authenticatorConfig2; + private UserDefinedLocalAuthenticatorConfig authenticatorConfigForException; + private UserDefinedLocalAuthenticatorConfig authenticatorForUpdate; + private UserDefinedLocalAuthenticatorConfig authenticatorForUpdateForException; + + private static final String AUTHENTICATOR1_NAME = "auth1"; + private static final String AUTHENTICATOR2_NAME = "auth2"; + private static final String AUTHENTICATOR_CONFIG_FOR_EXCEPTION_NAME = "exception_auth"; + private static final String NON_EXIST_AUTHENTICATOR_NAME = "non_exist_auth"; + + private final AuthenticatorManagementDAOImpl authenticatorManagementDAO = new AuthenticatorManagementDAOImpl(); + + @BeforeClass + public void setUpClass() { + + authenticatorConfig1 = UserDefinedLocalAuthenticatorDataUtil.createUserDefinedAuthenticatorConfig + (AUTHENTICATOR1_NAME, AuthenticatorPropertyConstants.AuthenticationType.IDENTIFICATION); + authenticatorConfig2 = UserDefinedLocalAuthenticatorDataUtil.createUserDefinedAuthenticatorConfig( + AUTHENTICATOR2_NAME, AuthenticatorPropertyConstants.AuthenticationType.VERIFICATION); + authenticatorForUpdate = UserDefinedLocalAuthenticatorDataUtil.updateUserDefinedAuthenticatorConfig( + authenticatorConfig1); + authenticatorForUpdateForException = UserDefinedLocalAuthenticatorDataUtil + .updateUserDefinedAuthenticatorConfigForSQLException(authenticatorConfig1); + authenticatorConfigForException = UserDefinedLocalAuthenticatorDataUtil + .createUserDefinedAuthenticatorConfigForSQLException( + AUTHENTICATOR_CONFIG_FOR_EXCEPTION_NAME, + AuthenticatorPropertyConstants.AuthenticationType.IDENTIFICATION); + + } + + @DataProvider(name = "authenticatorConfig") + public Object[][] authenticatorConfig() { + + return new Object[][]{ + {authenticatorConfig1}, + {authenticatorConfig2} + }; + } + + @Test(dataProvider = "authenticatorConfig", priority = 1) + public void testAddUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticatorConfig config) + throws AuthenticatorMgtException { + + UserDefinedLocalAuthenticatorConfig createdAuthenticator = authenticatorManagementDAO + .addUserDefinedLocalAuthenticator(config, tenantId); + Assert.assertNotNull(createdAuthenticator); + Assert.assertEquals(createdAuthenticator.getName(), config.getName()); + Assert.assertEquals(createdAuthenticator.getDisplayName(), config.getDisplayName()); + Assert.assertEquals(createdAuthenticator.isEnabled(), config.isEnabled()); + Assert.assertEquals(createdAuthenticator.getDefinedByType(), config.getDefinedByType()); + } + + @Test(priority = 2) + public void testAddUserDefinedLocalAuthenticatorWithSQLException() { + + AuthenticatorMgtException exception = assertThrows(AuthenticatorMgtException.class, () -> + authenticatorManagementDAO.addUserDefinedLocalAuthenticator(authenticatorConfigForException, tenantId)); + Assert.assertEquals(exception.getErrorCode(), ERROR_WHILE_ADDING_AUTHENTICATOR.getCode()); + } + + @Test(priority = 15) + public void testAddUserDefinedLocalAuthenticatorWithOutActionProperty() { + + authenticatorConfigForException.setProperties(new Property[0]); + AuthenticatorMgtException exception = assertThrows(AuthenticatorMgtException.class, () -> + authenticatorManagementDAO.addUserDefinedLocalAuthenticator(authenticatorConfigForException, tenantId)); + Assert.assertEquals(exception.getErrorCode(), ERROR_WHILE_ADDING_AUTHENTICATOR.getCode()); + } + + @Test(priority = 19) + public void testUpdateUserDefinedLocalAuthenticator() throws AuthenticatorMgtException { + + UserDefinedLocalAuthenticatorConfig updatedConfig = authenticatorManagementDAO + .updateUserDefinedLocalAuthenticator(authenticatorConfig1, authenticatorForUpdate, tenantId); + Assert.assertNotNull(updatedConfig); + Assert.assertEquals(updatedConfig.getName(), authenticatorForUpdate.getName()); + Assert.assertEquals(updatedConfig.getDisplayName(), authenticatorForUpdate.getDisplayName()); + Assert.assertEquals(updatedConfig.isEnabled(), authenticatorForUpdate.isEnabled()); + Assert.assertEquals(updatedConfig.getDefinedByType(), authenticatorForUpdate.getDefinedByType()); + + authenticatorConfig1 = authenticatorForUpdate; + } + + @Test(priority = 21) + public void testUpdateUserDefinedLocalAuthenticatorForException() { + + AuthenticatorMgtException exception = assertThrows(AuthenticatorMgtException.class, () -> + authenticatorManagementDAO.updateUserDefinedLocalAuthenticator(authenticatorConfig1, + authenticatorForUpdateForException, tenantId)); + Assert.assertEquals(exception.getErrorCode(), ERROR_WHILE_UPDATING_AUTHENTICATOR.getCode()); + } + + @Test(dataProvider = "authenticatorConfig", priority = 31) + public void testGetUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticatorConfig config) + throws AuthenticatorMgtException { + + UserDefinedLocalAuthenticatorConfig retrievedConfig = authenticatorManagementDAO + .getUserDefinedLocalAuthenticator(config.getName(), tenantId); + Assert.assertNotNull(retrievedConfig); + Assert.assertEquals(retrievedConfig.getName(), config.getName()); + Assert.assertEquals(retrievedConfig.getDisplayName(), config.getDisplayName()); + Assert.assertEquals(retrievedConfig.isEnabled(), config.isEnabled()); + Assert.assertEquals(retrievedConfig.getDefinedByType(), config.getDefinedByType()); + } + + @Test(priority = 41) + public void testGetNonExistingUserDefinedLocalAuthenticator() throws AuthenticatorMgtException { + + UserDefinedLocalAuthenticatorConfig config = authenticatorManagementDAO.getUserDefinedLocalAuthenticator( + AUTHENTICATOR_CONFIG_FOR_EXCEPTION_NAME, tenantId); + + Assert.assertNull(config); + } + + @Test(priority = 51) + public void testGetUserDefinedLocalAuthenticatorForNonExist() throws AuthenticatorMgtException { + + Assert.assertNull(authenticatorManagementDAO.getUserDefinedLocalAuthenticator( + NON_EXIST_AUTHENTICATOR_NAME, tenantId)); + } + + @Test(dataProvider = "authenticatorConfig", priority = 134) + public void testDeleteUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticatorConfig config) + throws AuthenticatorMgtException { + + authenticatorManagementDAO.deleteUserDefinedLocalAuthenticator(config.getName(), config, tenantId); + Assert.assertNull(authenticatorManagementDAO.getUserDefinedLocalAuthenticator(config.getName(), tenantId)); + } +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/util/ActionMgtTestUtil.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/util/ActionMgtTestUtil.java index 108bfe4e0ce2..810cfd73a976 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/util/ActionMgtTestUtil.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/util/ActionMgtTestUtil.java @@ -18,17 +18,17 @@ package org.wso2.carbon.identity.application.common.model.test.util; +import org.wso2.carbon.identity.action.management.exception.ActionMgtException; import org.wso2.carbon.identity.action.management.model.Action; import org.wso2.carbon.identity.action.management.model.Authentication; import org.wso2.carbon.identity.action.management.model.EndpointConfig; -import org.wso2.carbon.identity.application.common.model.FederatedAuthenticatorConfig; -import org.wso2.carbon.identity.application.common.model.IdentityProvider; -import org.wso2.carbon.identity.application.common.model.Property; -import org.wso2.carbon.identity.application.common.model.UserDefinedAuthenticatorEndpointConfig; -import org.wso2.carbon.identity.application.common.model.UserDefinedFederatedAuthenticatorConfig; +import org.wso2.carbon.identity.action.management.service.ActionManagementService; -import java.util.HashMap; -import java.util.Map; +import static org.mockito.ArgumentMatchers.any; +import static org.mockito.ArgumentMatchers.anyString; +import static org.mockito.Mockito.doNothing; +import static org.mockito.Mockito.mock; +import static org.mockito.Mockito.when; public class ActionMgtTestUtil { @@ -55,42 +55,15 @@ public static EndpointConfig createEndpointConfig(String uri, String username, S return endpointConfigBuilder.build(); } - public static IdentityProvider createIdPWithUserDefinedFederatedAuthenticatorConfig(String idpName, - EndpointConfig endpointConfig) { + public static ActionManagementService mockActionService(Action action) throws ActionMgtException { - // Initialize Test Identity Provider 4 with custom user defined federated authenticator. - IdentityProvider newUserDefinedIdp = new IdentityProvider(); - newUserDefinedIdp.setIdentityProviderName(idpName); + ActionManagementService actionManagementService = mock(ActionManagementService.class); - UserDefinedFederatedAuthenticatorConfig userDefinedFederatedAuthenticatorConfig = new - UserDefinedFederatedAuthenticatorConfig(); - userDefinedFederatedAuthenticatorConfig.setDisplayName("DisplayName1"); - userDefinedFederatedAuthenticatorConfig.setName("customFedAuthenticator"); - userDefinedFederatedAuthenticatorConfig.setEnabled(true); - userDefinedFederatedAuthenticatorConfig.setEndpointConfig( - buildUserDefinedAuthenticatorEndpointConfig(endpointConfig)); - Property property = new Property(); - property.setName("actionId"); - property.setValue(ASSOCIATED_ACTION_ID); - property.setConfidential(false); - userDefinedFederatedAuthenticatorConfig.setProperties(new Property[]{property}); - newUserDefinedIdp.setFederatedAuthenticatorConfigs( - new FederatedAuthenticatorConfig[]{userDefinedFederatedAuthenticatorConfig}); - newUserDefinedIdp.setDefaultAuthenticatorConfig(userDefinedFederatedAuthenticatorConfig); - return newUserDefinedIdp; - } - - public static UserDefinedAuthenticatorEndpointConfig buildUserDefinedAuthenticatorEndpointConfig( - EndpointConfig endpointConfig) { + when(actionManagementService.addAction(anyString(), any(), any())).thenReturn(action); + when(actionManagementService.updateAction(anyString(), any(), any(), any())).thenReturn(action); + when(actionManagementService.getActionByActionId(anyString(), any(), any())).thenReturn(action); + doNothing().when(actionManagementService).deleteAction(anyString(), any(), any()); - UserDefinedAuthenticatorEndpointConfig.UserDefinedAuthenticatorEndpointConfigBuilder endpointConfigBuilder = - new UserDefinedAuthenticatorEndpointConfig.UserDefinedAuthenticatorEndpointConfigBuilder(); - endpointConfigBuilder.uri(endpointConfig.getUri()); - endpointConfigBuilder.authenticationType(endpointConfig.getAuthentication().getType().getName()); - Map propMap = new HashMap<>(); - endpointConfig.getAuthentication().getProperties() - .forEach(prop -> propMap.put(prop.getName(), prop.getValue())); - endpointConfigBuilder.authenticationProperties(propMap); - return endpointConfigBuilder.build(); + return actionManagementService; } } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/util/UserDefinedLocalAuthenticatorDataUtil.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/util/UserDefinedLocalAuthenticatorDataUtil.java new file mode 100644 index 000000000000..52d82d6421ba --- /dev/null +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/util/UserDefinedLocalAuthenticatorDataUtil.java @@ -0,0 +1,164 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.com). + * + * WSO2 LLC. 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.identity.application.common.model.test.util; + +import com.google.gson.Gson; +import org.wso2.carbon.identity.action.management.model.Authentication; +import org.wso2.carbon.identity.application.common.model.LocalAuthenticatorConfig; +import org.wso2.carbon.identity.application.common.model.Property; +import org.wso2.carbon.identity.application.common.model.UserDefinedAuthenticatorEndpointConfig.UserDefinedAuthenticatorEndpointConfigBuilder; +import org.wso2.carbon.identity.application.common.model.UserDefinedLocalAuthenticatorConfig; +import org.wso2.carbon.identity.base.AuthenticatorPropertyConstants; + +import java.util.HashMap; + +public class UserDefinedLocalAuthenticatorDataUtil { + + private static final Gson gson = new Gson(); + + /** + * Create a user defined authenticator configuration. + * + * @param uniqueIdentifier Unique identifier for the authenticator. + * @param type Authentication type. + * @return UserDefinedLocalAuthenticatorConfig + */ + public static UserDefinedLocalAuthenticatorConfig createUserDefinedAuthenticatorConfig(String uniqueIdentifier, + AuthenticatorPropertyConstants.AuthenticationType type) { + + UserDefinedLocalAuthenticatorConfig authenticatorConfig = new + UserDefinedLocalAuthenticatorConfig(AuthenticatorPropertyConstants.AuthenticationType.IDENTIFICATION); + authenticatorConfig.setName(uniqueIdentifier); + authenticatorConfig.setDisplayName("Custom " + uniqueIdentifier); + authenticatorConfig.setEnabled(true); + authenticatorConfig.setDefinedByType(AuthenticatorPropertyConstants.DefinedByType.USER); + authenticatorConfig.setAuthenticationType(type); + authenticatorConfig.setProperties(buildAuthenticatorProperties()); + UserDefinedAuthenticatorEndpointConfigBuilder endpointConfigBuilder = buildAuthenticatorEndpointConfig(); + authenticatorConfig.setEndpointConfig(endpointConfigBuilder.build()); + + return authenticatorConfig; + } + + /** + * Create a system defined authenticator configuration. + * + * @param uniqueIdentifier Unique identifier for the authenticator. + * @return LocalAuthenticatorConfig + */ + public static LocalAuthenticatorConfig createSystemDefinedAuthenticatorConfig(String uniqueIdentifier) { + + LocalAuthenticatorConfig authenticatorConfig = new LocalAuthenticatorConfig(); + authenticatorConfig.setName(uniqueIdentifier); + authenticatorConfig.setDisplayName("Custom " + uniqueIdentifier); + authenticatorConfig.setEnabled(true); + authenticatorConfig.setDefinedByType(AuthenticatorPropertyConstants.DefinedByType.SYSTEM); + Property prop1 = new Property(); + prop1.setName("PropertyName1_" + uniqueIdentifier); + prop1.setValue("PropertyValue1_" + uniqueIdentifier); + prop1.setConfidential(false); + Property prop2 = new Property(); + prop2.setName("PropertyName2_" + uniqueIdentifier); + prop2.setValue("PropertyValue2_" + uniqueIdentifier); + prop2.setConfidential(true); + authenticatorConfig.setProperties(new Property[]{prop1, prop2}); + + return authenticatorConfig; + } + + /** + * Create a user defined authenticator configuration for an SQL exception. + * + * @param uniqueIdentifier Unique identifier for the authenticator. + * @param type Authentication type. + * @return UserDefinedLocalAuthenticatorConfig + */ + public static UserDefinedLocalAuthenticatorConfig createUserDefinedAuthenticatorConfigForSQLException( + String uniqueIdentifier, AuthenticatorPropertyConstants.AuthenticationType type) { + + UserDefinedLocalAuthenticatorConfig authenticatorConfigForException = + createUserDefinedAuthenticatorConfig(uniqueIdentifier, type); + authenticatorConfigForException.setDisplayName("Authenticator name with 254 characters".repeat(50)); + + return authenticatorConfigForException; + } + + /** + * Build the endpoint configuration for the user defined authenticator. + * + * @return UserDefinedAuthenticatorEndpointConfigBuilder + */ + public static UserDefinedAuthenticatorEndpointConfigBuilder buildAuthenticatorEndpointConfig() { + + UserDefinedAuthenticatorEndpointConfigBuilder endpointConfigBuilder = + new UserDefinedAuthenticatorEndpointConfigBuilder(); + endpointConfigBuilder.uri("https://localhost:8080/test"); + endpointConfigBuilder.authenticationType(Authentication.Type.BASIC.getName()); + HashMap authProperties = new HashMap<>(); + authProperties.put("username", "admin"); + authProperties.put("password", "admin"); + endpointConfigBuilder.authenticationProperties(authProperties); + return endpointConfigBuilder; + } + + /** + * Update the user defined authenticator configuration. + * + * @param authenticatorConfig UserDefinedLocalAuthenticatorConfig + * @return UserDefinedLocalAuthenticatorConfig + */ + public static UserDefinedLocalAuthenticatorConfig updateUserDefinedAuthenticatorConfig( + UserDefinedLocalAuthenticatorConfig authenticatorConfig) { + + UserDefinedLocalAuthenticatorConfig updatingConfig = gson.fromJson(gson.toJson(authenticatorConfig), + UserDefinedLocalAuthenticatorConfig.class); + updatingConfig.setName(authenticatorConfig.getName()); + updatingConfig.setDisplayName("UpdatedDisplayName"); + updatingConfig.setEnabled(false); + + return updatingConfig; + } + + public static UserDefinedLocalAuthenticatorConfig updateUserDefinedAuthenticatorConfigForSQLException( + UserDefinedLocalAuthenticatorConfig authenticatorConfig) { + + UserDefinedLocalAuthenticatorConfig updatingConfig = gson.fromJson(gson.toJson(authenticatorConfig), + UserDefinedLocalAuthenticatorConfig.class); + updatingConfig.setName(authenticatorConfig.getName()); + updatingConfig.setEnabled(false); + updatingConfig.setDisplayName("Authenticator name with 254 characters".repeat(50)); + + return updatingConfig; + } + + + /** + * Build the properties for the user defined authenticator. + * + * @return Property[] + */ + public static Property[] buildAuthenticatorProperties() { + + Property property = new Property(); + property.setName("actionId"); + property.setValue("actionId"); + + return new Property[]{property}; + } +} diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/testng.xml b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/testng.xml index 9512040a62d7..5e099dcc02ab 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/testng.xml +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/resources/testng.xml @@ -17,9 +17,10 @@ - + + From 1dc07af3a5a602c01fe0f54518d5a126339e12ca Mon Sep 17 00:00:00 2001 From: Thisara-Welmilla Date: Thu, 12 Dec 2024 11:05:14 +0530 Subject: [PATCH 08/15] Improvement with cross component transactions. --- .../impl/AuthenticatorManagementDAOImpl.java | 87 +++++++++---------- .../impl/AuthenticatorManagementFacade.java | 38 +++++--- 2 files changed, 71 insertions(+), 54 deletions(-) diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java index bdb532e39a6c..6d7549e4f79d 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java @@ -21,7 +21,6 @@ import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.wso2.carbon.database.utils.jdbc.NamedJdbcTemplate; -import org.wso2.carbon.database.utils.jdbc.NamedPreparedStatement; import org.wso2.carbon.database.utils.jdbc.exceptions.DataAccessException; import org.wso2.carbon.identity.application.common.constant.AuthenticatorMgtSQLConstants.Column; import org.wso2.carbon.identity.application.common.constant.AuthenticatorMgtSQLConstants.Query; @@ -36,9 +35,6 @@ import org.wso2.carbon.identity.core.util.IdentityDatabaseUtil; import org.wso2.carbon.identity.core.util.IdentityTenantUtil; -import java.sql.Connection; -import java.sql.ResultSet; -import java.sql.SQLException; import java.util.ArrayList; import java.util.List; @@ -120,7 +116,6 @@ public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator( public UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator( String authenticatorConfigName, int tenantId) throws AuthenticatorMgtException { - Connection dbConnection = IdentityDatabaseUtil.getDBConnection(false); try { return getUserDefinedLocalAuthenticatorByName(authenticatorConfigName, tenantId); } catch (DataAccessException e) { @@ -129,8 +124,6 @@ public UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator( "domain: %s.", authenticatorConfigName, IdentityTenantUtil.getTenantDomain(tenantId))); } throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_RETRIEVING_AUTHENTICATOR_BY_NAME, e); - } finally { - IdentityDatabaseUtil.closeConnection(dbConnection); } } @@ -138,46 +131,31 @@ public UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator( public List getAllUserDefinedLocalAuthenticators(int tenantId) throws AuthenticatorMgtException { - try (Connection dbConnection = IdentityDatabaseUtil.getDBConnection(true); - NamedPreparedStatement statement = new NamedPreparedStatement(dbConnection, - Query.GET_ALL_USER_DEFINED_AUTHENTICATOR_SQL)) { - statement.setString(Column.DEFINED_BY, DefinedByType.USER.toString()); - statement.setInt(Column.TENANT_ID, tenantId); + List allUserDefinedLocalConfigs = new ArrayList<>(); + try { + NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); + jdbcTemplate.executeQuery(Query.GET_ALL_USER_DEFINED_AUTHENTICATOR_SQL, + (resultSet, rowNumber) -> { + UserDefinedLocalAuthenticatorConfig config = getLocalAuthenticatorConfigBasedOnType( + resultSet.getString(Column.AUTHENTICATION_TYPE)); + config.setName(resultSet.getString(Column.NAME)); + config.setDisplayName(resultSet.getString(Column.DISPLAY_NAME)); + config.setEnabled(resultSet.getString(Column.IS_ENABLED).equals(IS_TRUE_VALUE)); + config.setDefinedByType(DefinedByType.valueOf(resultSet.getString(Column.DEFINED_BY))); + allUserDefinedLocalConfigs.add(config); + return null; + }, + statement -> { + statement.setString(Column.DEFINED_BY, DefinedByType.USER.toString()); + statement.setInt(Column.TENANT_ID, tenantId); + }); - List allUserDefinedLocalConfigs = new ArrayList<>(); - try (ResultSet rs = statement.executeQuery()) { - while (rs.next()) { - UserDefinedLocalAuthenticatorConfig config = getLocalAuthenticatorConfigBasedOnType( - rs.getString(Column.AUTHENTICATION_TYPE)); - config.setName(rs.getString(Column.NAME)); - config.setDisplayName(rs.getString(Column.DISPLAY_NAME)); - config.setEnabled(rs.getString(Column.IS_ENABLED).equals(IS_TRUE_VALUE)); - config.setDefinedByType(DefinedByType.valueOf(rs.getString(Column.DEFINED_BY))); - - int authenticatorConfigID = getAuthenticatorIdentifier(config.getName(), tenantId); - try (NamedPreparedStatement statementProp = new NamedPreparedStatement(dbConnection, - Query.GET_AUTHENTICATOR_PROP_SQL)) { - statementProp.setInt(Column.AUTHENTICATOR_ID, authenticatorConfigID); - statementProp.setInt(Column.TENANT_ID, tenantId); - - try (ResultSet rsProp = statementProp.executeQuery()) { - List properties = new ArrayList<>(); - while (rsProp.next()) { - Property property = new Property(); - property.setName(rsProp.getString(Column.PROPERTY_KEY)); - property.setValue(rsProp.getString(Column.PROPERTY_VALUE)); - property.setConfidential(false); - properties.add(property); - } - config.setProperties(properties.toArray(new Property[0])); - } - } - - allUserDefinedLocalConfigs.add(config); - } + for (UserDefinedLocalAuthenticatorConfig retrievedConfigs: allUserDefinedLocalConfigs) { + int authenticatorConfigID = getAuthenticatorIdentifier(retrievedConfigs.getName(), tenantId); + retrievedConfigs.setProperties(getAuthenticatorProperties(authenticatorConfigID, tenantId)); } return allUserDefinedLocalConfigs; - } catch (SQLException | DataAccessException e) { + } catch (DataAccessException e) { if (LOG.isDebugEnabled()) { LOG.debug(String.format("Error while retrieving the all user defined local authenticators in tenant " + "domain: %s.", IdentityTenantUtil.getTenantDomain(tenantId))); @@ -301,4 +279,25 @@ private void addAuthenticatorProperties(String authenticatorName, int authentica } }), null, false); } + + private Property[] getAuthenticatorProperties(int authenticatorConfigID, + int tenantId) throws DataAccessException { + + List properties = new ArrayList<>(); + NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); + jdbcTemplate.executeQuery(Query.GET_AUTHENTICATOR_PROP_SQL, + (resultSet, rowNumber) -> { + Property property = new Property(); + property.setName(resultSet.getString(Column.PROPERTY_KEY)); + property.setValue(resultSet.getString(Column.PROPERTY_VALUE)); + property.setConfidential(false); + properties.add(property); + return null; + }, + statementProp -> { + statementProp.setInt(Column.AUTHENTICATOR_ID, authenticatorConfigID); + statementProp.setInt(Column.TENANT_ID, tenantId); + }); + return properties.toArray(new Property[0]); + } } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java index f9f885557e1a..901a3fd64b1b 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java @@ -87,9 +87,8 @@ public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator(U }); } catch (TransactionException e) { // Since exceptions thrown are wrapped with TransactionException, extracting the actual cause. - LOG.debug("Error while updating the user defined local authenticator: " + - newAuthenticatorConfig.getName() + " in Tenant Domain: " + - IdentityTenantUtil.getTenantDomain(tenantId) + + LOG.debug("Error while updating the user defined local authenticator: " + newAuthenticatorConfig + .getName() + " in Tenant Domain: " + IdentityTenantUtil.getTenantDomain(tenantId) + ". Rolling back updated authenticator information, and associated action."); throw handleAuthenticatorMgtException(e.getCause()); } @@ -99,20 +98,39 @@ public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator(U public UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator( String authenticatorConfigName, int tenantId) throws AuthenticatorMgtException { - UserDefinedLocalAuthenticatorConfig config = dao.getUserDefinedLocalAuthenticator(authenticatorConfigName, - tenantId); - return endpointConfigManager.resolveEndpointConfigurations(config, tenantId); + NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); + try { + return jdbcTemplate.withTransaction(template -> + endpointConfigManager.resolveEndpointConfigurations(dao.getUserDefinedLocalAuthenticator( + authenticatorConfigName, tenantId), tenantId)); + } catch (TransactionException e) { + // Since exceptions thrown are wrapped with TransactionException, extracting the actual cause. + LOG.debug("Error while retrieving the user defined local authenticator: " + authenticatorConfigName + + " in Tenant Domain: " + IdentityTenantUtil.getTenantDomain(tenantId)); + throw handleAuthenticatorMgtException(e.getCause()); + } } @Override public List getAllUserDefinedLocalAuthenticators(int tenantId) throws AuthenticatorMgtException { - List configList = dao.getAllUserDefinedLocalAuthenticators(tenantId); - for (UserDefinedLocalAuthenticatorConfig config : configList) { - endpointConfigManager.resolveEndpointConfigurations(config, tenantId); + NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); + try { + return jdbcTemplate.withTransaction(template -> { + List configList = + dao.getAllUserDefinedLocalAuthenticators(tenantId); + for (UserDefinedLocalAuthenticatorConfig config : configList) { + endpointConfigManager.resolveEndpointConfigurations(config, tenantId); + } + return configList; + }); + } catch (TransactionException e) { + // Since exceptions thrown are wrapped with TransactionException, extracting the actual cause. + LOG.debug("Error while retrieving all user defined local authenticators in Tenant Domain: " + + IdentityTenantUtil.getTenantDomain(tenantId)); + throw handleAuthenticatorMgtException(e.getCause()); } - return configList; } @Override From 664de74ed061c2a47ba958b12d404ca2c1c56584 Mon Sep 17 00:00:00 2001 From: Thisara-Welmilla Date: Thu, 12 Dec 2024 11:59:42 +0530 Subject: [PATCH 09/15] Add permissions and scopes. --- .../resources/identity.xml | 13 +++++++++++++ .../resources/identity.xml.j2 | 12 ++++++++++++ .../resources/resource-access-control-v2.xml | 11 +++++++++++ .../resources/resource-access-control-v2.xml.j2 | 11 +++++++++++ 4 files changed, 47 insertions(+) diff --git a/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/identity.xml b/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/identity.xml index 1eafa77d3c41..cb2727a4e620 100644 --- a/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/identity.xml +++ b/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/identity.xml @@ -2315,6 +2315,19 @@ internal_action_mgt_view + + /permission/admin/manage/custom_authenticator/create + internal_custom_authenticator_create + + + /permission/admin/manage/custom_authenticator/update + internal_custom_authenticator_update + + + /permission/admin/manage/custom_authenticator/delete + internal_custom_authenticator_delete + + diff --git a/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/identity.xml.j2 b/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/identity.xml.j2 index 6bc08bc9a482..90e7d3aa010a 100644 --- a/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/identity.xml.j2 +++ b/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/identity.xml.j2 @@ -3574,6 +3574,18 @@ internal_action_mgt_view + + /permission/admin/manage/custom_authenticator/create + internal_custom_authenticator_create + + + /permission/admin/manage/custom_authenticator/update + internal_custom_authenticator_update + + + /permission/admin/manage/custom_authenticator/delete + internal_custom_authenticator_delete + diff --git a/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/resource-access-control-v2.xml b/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/resource-access-control-v2.xml index 92659d558bfc..f6888d5371b0 100644 --- a/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/resource-access-control-v2.xml +++ b/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/resource-access-control-v2.xml @@ -1207,6 +1207,17 @@ internal_rule_metadata_view + + + internal_custom_authenticator_create + + + internal_custom_authenticator_update + + + internal_custom_authenticator_delete + + diff --git a/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/resource-access-control-v2.xml.j2 b/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/resource-access-control-v2.xml.j2 index cb0764b2f945..13035ed3a86d 100644 --- a/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/resource-access-control-v2.xml.j2 +++ b/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/resource-access-control-v2.xml.j2 @@ -1271,6 +1271,17 @@ internal_rule_metadata_view + + + internal_custom_authenticator_create + + + internal_custom_authenticator_update + + + internal_custom_authenticator_delete + + From 4300b0fd1c541a4aafaa3cbed78fb3ee3655e583 Mon Sep 17 00:00:00 2001 From: Thisara-Welmilla Date: Thu, 12 Dec 2024 15:57:13 +0530 Subject: [PATCH 10/15] Addressed comments. --- .../ApplicationAuthenticatorService.java | 3 +- .../common/cache/AuthenticatorCacheEntry.java | 2 + .../common/cache/AuthenticatorCacheKey.java | 2 + .../dao/AuthenticatorManagementDAO.java | 9 +- .../impl/AuthenticatorManagementDAOImpl.java | 66 ++-------- .../impl/AuthenticatorManagementFacade.java | 114 ++++++++++++------ .../impl/CacheBackedAuthenticatorMgtDAO.java | 25 +++- .../AuthenticatorMgtExceptionBuilder.java | 20 +-- .../util/IdentityApplicationConstants.java | 1 + ...nedAuthenticatorEndpointConfigManager.java | 42 +++++-- .../ApplicationAuthenticatorServiceTest.java | 61 ++++++---- .../AuthenticatorManagementDAOImplTest.java | 14 +-- .../resources/system-api-resource.xml | 12 ++ .../resources/system-api-resource.xml.j2 | 12 ++ .../resources/identity.xml | 6 +- .../resources/identity.xml.j2 | 6 +- .../resources/resource-access-control-v2.xml | 6 +- .../resource-access-control-v2.xml.j2 | 6 +- 18 files changed, 249 insertions(+), 158 deletions(-) diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java index 4178341b9954..92674282267c 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/ApplicationAuthenticatorService.java @@ -38,13 +38,13 @@ import static org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.buildClientException; import static org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.buildRuntimeServerException; +import static org.wso2.carbon.identity.application.common.util.IdentityApplicationConstants.Authenticator.DISPLAY_NAME; /** * Application authenticator service. */ public class ApplicationAuthenticatorService { - private static final String DISPLAY_NAME = "Display name"; private static volatile ApplicationAuthenticatorService instance; private static final Log LOG = LogFactory.getLog(ApplicationAuthenticatorService.class); private static final AuthenticatorManagementDAO dao = @@ -74,6 +74,7 @@ public List getLocalAuthenticators() { /** * This returns user defined local authenticators. * + * @param tenantDomain Tenant domain. * @return Retrieved LocalAuthenticatorConfig. */ public List getAllUserDefinedLocalAuthenticators(String tenantDomain) diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCacheEntry.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCacheEntry.java index 31b29923ecd0..9529cd3aba92 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCacheEntry.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCacheEntry.java @@ -26,6 +26,8 @@ */ public class AuthenticatorCacheEntry extends CacheEntry { + private static final long serialVersionUID = -6234723984328871924L; + private UserDefinedLocalAuthenticatorConfig authenticatorConfig; public AuthenticatorCacheEntry(UserDefinedLocalAuthenticatorConfig authenticatorConfig) { diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCacheKey.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCacheKey.java index 849aade9b671..645fda5227af 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCacheKey.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/cache/AuthenticatorCacheKey.java @@ -25,6 +25,8 @@ */ public class AuthenticatorCacheKey extends CacheKey { + private static final long serialVersionUID = -2897123859023483921L; + private final String authenticatorName; public AuthenticatorCacheKey(String authenticatorName) { diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/AuthenticatorManagementDAO.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/AuthenticatorManagementDAO.java index 32b406995cd6..292a22192948 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/AuthenticatorManagementDAO.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/AuthenticatorManagementDAO.java @@ -33,7 +33,6 @@ public interface AuthenticatorManagementDAO { * * @param authenticatorConfig Local application authenticator configuration. * @param tenantId Tenant Id. - * * @return Created UserDefinedLocalAuthenticatorConfig. * @throws AuthenticatorMgtException If an error occurs while adding the authenticator configuration. */ @@ -46,7 +45,6 @@ UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( * @param existingAuthenticatorConfig Existing Local application authenticator configuration. * @param updatedAuthenticatorConfig New local application authenticator configuration. * @param tenantId Tenant Id. - * * @return Updated UserDefinedLocalAuthenticatorConfig. * @throws AuthenticatorMgtException If an error occurs while updating the authenticator configuration. */ @@ -56,11 +54,10 @@ UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator( throws AuthenticatorMgtException; /** - * Retrieve a Local user defined Application Authenticator configuration by name. + * Retrieve a local user defined application authenticator configuration by name. * * @param authenticatorConfigName Name of the local application authenticator configuration. * @param tenantId Tenant Id. - * * @return Retrieved UserDefinedLocalAuthenticatorConfig * @throws AuthenticatorMgtException If an error occurs while retrieving the authenticator configuration. */ @@ -70,8 +67,7 @@ UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator( /** * Retrieve all user defined local application authenticator configurations. * - * @param tenantId Tenant Id. - * + * @param tenantId Tenant Id. * @return Retrieved UserDefinedLocalAuthenticatorConfig * @throws AuthenticatorMgtException If an error occurs while retrieving the authenticator configurations. */ @@ -83,7 +79,6 @@ List getAllUserDefinedLocalAuthenticators(i * * @param authenticatorConfigName Name of the local application authenticator configuration. * @param tenantId Tenant Id. - * * @throws AuthenticatorMgtException If an error occurs while deleting the authenticator configuration. */ void deleteUserDefinedLocalAuthenticator(String authenticatorConfigName, UserDefinedLocalAuthenticatorConfig diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java index 6d7549e4f79d..ed953197c3a5 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java @@ -18,8 +18,6 @@ package org.wso2.carbon.identity.application.common.dao.impl; -import org.apache.commons.logging.Log; -import org.apache.commons.logging.LogFactory; import org.wso2.carbon.database.utils.jdbc.NamedJdbcTemplate; import org.wso2.carbon.database.utils.jdbc.exceptions.DataAccessException; import org.wso2.carbon.identity.application.common.constant.AuthenticatorMgtSQLConstants.Column; @@ -33,20 +31,17 @@ import org.wso2.carbon.identity.base.AuthenticatorPropertyConstants.AuthenticationType; import org.wso2.carbon.identity.base.AuthenticatorPropertyConstants.DefinedByType; import org.wso2.carbon.identity.core.util.IdentityDatabaseUtil; -import org.wso2.carbon.identity.core.util.IdentityTenantUtil; import java.util.ArrayList; import java.util.List; import static org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.buildServerException; -import static org.wso2.carbon.identity.application.common.util.IdentityApplicationConstants.Authenticator.ACTION_ID_PROPERTY; /** * This class implements the AuthenticatorManagementDAO interface which perform CRUD operation on database. */ public class AuthenticatorManagementDAOImpl implements AuthenticatorManagementDAO { - private static final Log LOG = LogFactory.getLog(AuthenticatorManagementDAOImpl.class); public static final String IS_TRUE_VALUE = "1"; public static final String IS_FALSE_VALUE = "0"; public static final String LOCAL_IDP_NAME = "LOCAL"; @@ -69,17 +64,11 @@ public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( statement.setInt(Column.TENANT_ID, tenantId); }), null, false); - int authenticatorConfigID = getAuthenticatorIdentifier(authenticatorConfig.getName(), tenantId); - addAuthenticatorProperties(authenticatorConfig.getName(), authenticatorConfigID, - authenticatorConfig.getProperties(), tenantId); + int authenticatorConfigID = getAuthenticatorEntryId(authenticatorConfig.getName(), tenantId); + addAuthenticatorProperty(authenticatorConfigID, authenticatorConfig.getProperties(), tenantId); return getUserDefinedLocalAuthenticatorByName(authenticatorConfig.getName(), tenantId); } catch (DataAccessException e) { - if (LOG.isDebugEnabled()) { - LOG.debug(String.format("Error while adding the authenticator: %s in tenant domain: %s. " + - "Rolling back added Authenticator information.", authenticatorConfig.getName(), - IdentityTenantUtil.getTenantDomain(tenantId))); - } throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_ADDING_AUTHENTICATOR, e); } } @@ -103,11 +92,6 @@ public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator( return getUserDefinedLocalAuthenticatorByName(updatedAuthenticatorConfig.getName(), tenantId); } catch (DataAccessException e) { - if (LOG.isDebugEnabled()) { - LOG.debug(String.format("Error while updating the authenticator: %s in tenant domain: %s. " + - "Rolling back updated Authenticator information.", - existingAuthenticatorConfig.getName(), IdentityTenantUtil.getTenantDomain(tenantId))); - } throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_UPDATING_AUTHENTICATOR, e); } } @@ -119,10 +103,6 @@ public UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator( try { return getUserDefinedLocalAuthenticatorByName(authenticatorConfigName, tenantId); } catch (DataAccessException e) { - if (LOG.isDebugEnabled()) { - LOG.debug(String.format("Error while retrieving the user defined local authenticator:%s in tenant " + - "domain: %s.", authenticatorConfigName, IdentityTenantUtil.getTenantDomain(tenantId))); - } throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_RETRIEVING_AUTHENTICATOR_BY_NAME, e); } } @@ -151,15 +131,11 @@ public List getAllUserDefinedLocalAuthentic }); for (UserDefinedLocalAuthenticatorConfig retrievedConfigs: allUserDefinedLocalConfigs) { - int authenticatorConfigID = getAuthenticatorIdentifier(retrievedConfigs.getName(), tenantId); + int authenticatorConfigID = getAuthenticatorEntryId(retrievedConfigs.getName(), tenantId); retrievedConfigs.setProperties(getAuthenticatorProperties(authenticatorConfigID, tenantId)); } return allUserDefinedLocalConfigs; } catch (DataAccessException e) { - if (LOG.isDebugEnabled()) { - LOG.debug(String.format("Error while retrieving the all user defined local authenticators in tenant " + - "domain: %s.", IdentityTenantUtil.getTenantDomain(tenantId))); - } throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_RETRIEVING_AUTHENTICATOR_BY_NAME, e); } } @@ -170,7 +146,6 @@ public void deleteUserDefinedLocalAuthenticator(String authenticatorConfigName, NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); try { - jdbcTemplate.executeUpdate(Query.DELETE_AUTHENTICATOR_SQL, statement -> { statement.setString(Column.NAME, authenticatorConfigName); @@ -178,11 +153,6 @@ public void deleteUserDefinedLocalAuthenticator(String authenticatorConfigName, statement.executeUpdate(); }); } catch (DataAccessException e) { - if (LOG.isDebugEnabled()) { - LOG.debug(String.format("Error while deleting the authenticator: %s in tenant domain: %s. " + - "Rolling back deleted Authenticator information.", authenticatorConfigName, - IdentityTenantUtil.getTenantDomain(tenantId))); - } throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_DELETING_AUTHENTICATOR, e); } } @@ -211,7 +181,7 @@ private UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticatorByNa return null; } - int authenticatorConfigID = getAuthenticatorIdentifier(authenticatorConfigName, tenantId); + int authenticatorConfigID = getAuthenticatorEntryId(authenticatorConfigName, tenantId); List properties = new ArrayList<>(); jdbcTemplate.fetchSingleRecord(Query.GET_AUTHENTICATOR_PROP_SQL, (resultSet, rowNumber) -> { @@ -238,31 +208,26 @@ private UserDefinedLocalAuthenticatorConfig getLocalAuthenticatorConfigBasedOnTy return new UserDefinedLocalAuthenticatorConfig(AuthenticationType.IDENTIFICATION); } - private int getAuthenticatorIdentifier(String authenticatorConfigName, int tenantId) + private int getAuthenticatorEntryId(String authenticatorConfigName, int tenantId) throws AuthenticatorMgtServerException, DataAccessException { NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); - String id = jdbcTemplate.fetchSingleRecord(Query.GET_AUTHENTICATOR_ID_SQL, - (resultSet, rowNumber) -> resultSet.getString(Column.ID), + int id = jdbcTemplate.fetchSingleRecord(Query.GET_AUTHENTICATOR_ID_SQL, + (resultSet, rowNumber) -> resultSet.getInt(Column.ID), statement -> { statement.setString(Column.NAME, authenticatorConfigName); statement.setInt(Column.TENANT_ID, tenantId); }); - if (id != null) { - return Integer.parseInt(id); + if (id != 0) { + return id; } throw buildServerException(AuthenticatorMgtError.ERROR_CODE_NO_AUTHENTICATOR_FOUND, authenticatorConfigName); } - private void addAuthenticatorProperties(String authenticatorName, int authenticatorConfigID, Property[] properties, - int tenantId) throws DataAccessException, AuthenticatorMgtServerException { - - if (!(properties.length == 1 && ACTION_ID_PROPERTY.equals(properties[0].getName()))) { - throw buildServerException(AuthenticatorMgtError.ERROR_CODE_HAVING_MULTIPLE_PROP, - authenticatorName); - } + private void addAuthenticatorProperty(int authenticatorConfigID, Property[] properties, int tenantId) + throws DataAccessException { Property prop = properties[0]; NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); @@ -272,16 +237,11 @@ private void addAuthenticatorProperties(String authenticatorName, int authentica statementProp.setInt(Column.TENANT_ID, tenantId); statementProp.setString(Column.PROPERTY_KEY, prop.getName()); statementProp.setString(Column.PROPERTY_VALUE, prop.getValue()); - if (prop.isConfidential()) { - statementProp.setString(Column.IS_SECRET, IS_TRUE_VALUE); - } else { - statementProp.setString(Column.IS_SECRET, IS_FALSE_VALUE); - } + statementProp.setString(Column.IS_SECRET, IS_FALSE_VALUE); }), null, false); } - private Property[] getAuthenticatorProperties(int authenticatorConfigID, - int tenantId) throws DataAccessException { + private Property[] getAuthenticatorProperties(int authenticatorConfigID, int tenantId) throws DataAccessException { List properties = new ArrayList<>(); NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java index 901a3fd64b1b..ec8da806088d 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java @@ -18,29 +18,31 @@ package org.wso2.carbon.identity.application.common.dao.impl; -import org.apache.commons.logging.Log; -import org.apache.commons.logging.LogFactory; +import org.apache.commons.lang.StringUtils; import org.wso2.carbon.database.utils.jdbc.NamedJdbcTemplate; import org.wso2.carbon.database.utils.jdbc.exceptions.TransactionException; import org.wso2.carbon.identity.application.common.dao.AuthenticatorManagementDAO; import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtClientException; import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtException; import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtServerException; +import org.wso2.carbon.identity.application.common.model.Property; import org.wso2.carbon.identity.application.common.model.UserDefinedLocalAuthenticatorConfig; +import org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder; +import org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.AuthenticatorMgtError; import org.wso2.carbon.identity.application.common.util.UserDefinedAuthenticatorEndpointConfigManager; import org.wso2.carbon.identity.core.util.IdentityDatabaseUtil; -import org.wso2.carbon.identity.core.util.IdentityTenantUtil; import java.util.List; +import static org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.buildServerException; +import static org.wso2.carbon.identity.application.common.util.IdentityApplicationConstants.Authenticator.ACTION_ID_PROPERTY; + /** * This class responsible for managing authenticator endpoint configurations for the user defined local * authenticators. */ public class AuthenticatorManagementFacade implements AuthenticatorManagementDAO { - private static final Log LOG = LogFactory.getLog(AuthenticatorManagementFacade.class); - private final AuthenticatorManagementDAO dao; private UserDefinedAuthenticatorEndpointConfigManager endpointConfigManager = new UserDefinedAuthenticatorEndpointConfigManager(); @@ -50,6 +52,15 @@ public AuthenticatorManagementFacade(AuthenticatorManagementDAO dao) { this.dao = dao; } + /** + * Invoke external service to store associated data (endpoint configuration) and create the user defined local + * authenticator to the DB. + * + * @param authenticatorConfig User defined local authenticator configuration. + * @param tenantId Tenant ID. + * @return User defined local authenticator configuration. + * @throws AuthenticatorMgtException If an error occurs while adding the user defined local authenticator. + */ @Override public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( UserDefinedLocalAuthenticatorConfig authenticatorConfig, int tenantId) throws AuthenticatorMgtException { @@ -59,18 +70,26 @@ public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( try { return jdbcTemplate.withTransaction(template -> { endpointConfigManager.addEndpointConfigurations(authenticatorConfig, tenantId); + validateAuthenticatorProperties(authenticatorConfig); return endpointConfigManager.resolveEndpointConfigurations( dao.addUserDefinedLocalAuthenticator(authenticatorConfig, tenantId), tenantId); }); } catch (TransactionException e) { - // Since exceptions thrown are wrapped with TransactionException, extracting the actual cause. - LOG.debug("Error while creating the user defined local authenticator: " + authenticatorConfig.getName() + - " in Tenant Domain: " + IdentityTenantUtil.getTenantDomain(tenantId) + - ". Rolling back created authenticator information, and associated action."); - throw handleAuthenticatorMgtException(e.getCause()); + throw handleAuthenticatorMgtException(AuthenticatorMgtError.ERROR_WHILE_ADDING_AUTHENTICATOR, e, + authenticatorConfig.getName()); } } + /** + * Invoke external service to update associated data (endpoint configuration) and update the user defined local + * authenticator in DB. + * + * @param existingAuthenticatorConfig Existing user defined local authenticator configuration. + * @param newAuthenticatorConfig New user defined local authenticator configuration. + * @param tenantId Tenant ID. + * @return Updated user defined local authenticator configuration. + * @throws AuthenticatorMgtException If an error occurs while updating the user defined local authenticator. + */ @Override public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticatorConfig existingAuthenticatorConfig, UserDefinedLocalAuthenticatorConfig newAuthenticatorConfig, @@ -81,19 +100,26 @@ public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator(U return jdbcTemplate.withTransaction(template -> { endpointConfigManager.updateEndpointConfigurations(newAuthenticatorConfig, existingAuthenticatorConfig, tenantId); + validateAuthenticatorProperties(newAuthenticatorConfig); return endpointConfigManager.resolveEndpointConfigurations( dao.updateUserDefinedLocalAuthenticator(existingAuthenticatorConfig, newAuthenticatorConfig, tenantId), tenantId); }); } catch (TransactionException e) { - // Since exceptions thrown are wrapped with TransactionException, extracting the actual cause. - LOG.debug("Error while updating the user defined local authenticator: " + newAuthenticatorConfig - .getName() + " in Tenant Domain: " + IdentityTenantUtil.getTenantDomain(tenantId) + - ". Rolling back updated authenticator information, and associated action."); - throw handleAuthenticatorMgtException(e.getCause()); + throw handleAuthenticatorMgtException(AuthenticatorMgtError.ERROR_WHILE_UPDATING_AUTHENTICATOR, e, + newAuthenticatorConfig.getName()); } } + /** + * Get user defined local authenticator by name and resolving associated data (endpoint configurations) + * by invoking external service. + * + * @param authenticatorConfigName Name of the user defined local authenticator. + * @param tenantId Tenant ID. + * @return User defined local authenticator. + * @throws AuthenticatorMgtException If an error occurs while retrieving the user defined local authenticator. + */ @Override public UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator( String authenticatorConfigName, int tenantId) throws AuthenticatorMgtException { @@ -104,13 +130,19 @@ public UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator( endpointConfigManager.resolveEndpointConfigurations(dao.getUserDefinedLocalAuthenticator( authenticatorConfigName, tenantId), tenantId)); } catch (TransactionException e) { - // Since exceptions thrown are wrapped with TransactionException, extracting the actual cause. - LOG.debug("Error while retrieving the user defined local authenticator: " + authenticatorConfigName + - " in Tenant Domain: " + IdentityTenantUtil.getTenantDomain(tenantId)); - throw handleAuthenticatorMgtException(e.getCause()); + throw handleAuthenticatorMgtException(AuthenticatorMgtError.ERROR_WHILE_RETRIEVING_AUTHENTICATOR_BY_NAME, e, + authenticatorConfigName); } } + /** + * Get all user defined local authenticators and resolving associated data (endpoint configurations) + * by invoking external service. + * + * @param tenantId Tenant ID. + * @return List of user defined local authenticators. + * @throws AuthenticatorMgtException If an error occurs while retrieving all user defined local authenticators. + */ @Override public List getAllUserDefinedLocalAuthenticators(int tenantId) throws AuthenticatorMgtException { @@ -126,13 +158,20 @@ public List getAllUserDefinedLocalAuthentic return configList; }); } catch (TransactionException e) { - // Since exceptions thrown are wrapped with TransactionException, extracting the actual cause. - LOG.debug("Error while retrieving all user defined local authenticators in Tenant Domain: " + - IdentityTenantUtil.getTenantDomain(tenantId)); - throw handleAuthenticatorMgtException(e.getCause()); + throw handleAuthenticatorMgtException( + AuthenticatorMgtError.ERROR_WHILE_ALL_RETRIEVING_AUTHENTICATOR, e, StringUtils.EMPTY); } } + /** + * Invoke external service to delete associated data (endpoint configuration) and delete the user defined local + * authenticator in DB. + * + * @param authenticatorConfigName Name of the user defined local authenticator. + * @param authenticatorConfig User defined local authenticator configuration. + * @param tenantId Tenant ID. + * @throws AuthenticatorMgtException If an error occurs while deleting the user defined local authenticator. + */ @Override public void deleteUserDefinedLocalAuthenticator(String authenticatorConfigName, UserDefinedLocalAuthenticatorConfig authenticatorConfig, int tenantId) throws AuthenticatorMgtException { @@ -145,11 +184,8 @@ public void deleteUserDefinedLocalAuthenticator(String authenticatorConfigName, return null; }); } catch (TransactionException e) { - // Since exceptions thrown are wrapped with TransactionException, extracting the actual cause. - LOG.debug("Error while deleting the user defined local authenticator: " + authenticatorConfigName + - " in Tenant Domain: " + IdentityTenantUtil.getTenantDomain(tenantId) + - ". Rolling back deleted authenticator information, and associated action."); - throw handleAuthenticatorMgtException(e.getCause()); + throw handleAuthenticatorMgtException(AuthenticatorMgtError.ERROR_WHILE_DELETING_AUTHENTICATOR, e, + StringUtils.EMPTY); } } @@ -159,15 +195,25 @@ public void deleteUserDefinedLocalAuthenticator(String authenticatorConfigName, * @param throwable Throwable object. * @throws AuthenticatorMgtClientException If an authenticator management client exception. */ - private static AuthenticatorMgtException handleAuthenticatorMgtException(Throwable throwable) - throws AuthenticatorMgtException { + private static AuthenticatorMgtException handleAuthenticatorMgtException(AuthenticatorMgtError + authenticatorMgtError, Throwable throwable, String... data) throws AuthenticatorMgtException { - if (throwable instanceof AuthenticatorMgtClientException) { - AuthenticatorMgtClientException error = (AuthenticatorMgtClientException) throwable; + if (throwable.getCause() instanceof AuthenticatorMgtClientException) { + AuthenticatorMgtClientException error = (AuthenticatorMgtClientException) throwable.getCause(); throw new AuthenticatorMgtClientException(error.getErrorCode(), error.getMessage(), error.getDescription()); } - AuthenticatorMgtServerException error = (AuthenticatorMgtServerException) throwable; - throw new AuthenticatorMgtServerException(error.getErrorCode(), error.getMessage(), error.getDescription()); + throw buildServerException(authenticatorMgtError, throwable, data); + } + + private void validateAuthenticatorProperties(UserDefinedLocalAuthenticatorConfig authenticatorConfig) + throws AuthenticatorMgtServerException { + + // User defined local authenticator should have only one property which is the action id. + Property[] properties = authenticatorConfig.getProperties(); + if (!(properties.length == 1 && ACTION_ID_PROPERTY.equals(properties[0].getName()))) { + throw buildServerException(AuthenticatorMgtExceptionBuilder.AuthenticatorMgtError + .ERROR_CODE_HAVING_MULTIPLE_PROP, authenticatorConfig.getName()); + } } } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/CacheBackedAuthenticatorMgtDAO.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/CacheBackedAuthenticatorMgtDAO.java index d5e683b5752d..e4775e6583e8 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/CacheBackedAuthenticatorMgtDAO.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/CacheBackedAuthenticatorMgtDAO.java @@ -30,7 +30,7 @@ import java.util.List; /** - * This class implements the Cache backed AuthenticatorManagementDAO interface. + * Implements caching layer for the AuthenticatorManagementDAO. */ public class CacheBackedAuthenticatorMgtDAO implements AuthenticatorManagementDAO { @@ -53,6 +53,10 @@ public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( AuthenticatorCacheKey cacheKey = new AuthenticatorCacheKey(authenticatorConfig.getName()); authenticatorCache.addToCache(cacheKey, new AuthenticatorCacheEntry(createdConfig), tenantId); + if (LOG.isDebugEnabled()) { + LOG.debug(String.format( + "Adding cache entry for newly created authenticator %s.", authenticatorConfig.getName())); + } return createdConfig; } @@ -63,6 +67,10 @@ public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator(U AuthenticatorCacheKey cacheKey = new AuthenticatorCacheKey(existingAuthenticatorConfig.getName()); authenticatorCache.clearCacheEntry(cacheKey, tenantId); + if (LOG.isDebugEnabled()) { + LOG.debug(String.format( + "Delete cache entry of updating authenticator %s.", existingAuthenticatorConfig.getName())); + } return authenticatorMgtFacade.updateUserDefinedLocalAuthenticator( existingAuthenticatorConfig, newAuthenticatorConfig, tenantId); @@ -76,12 +84,24 @@ public UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator( AuthenticatorCacheEntry entry = authenticatorCache.getValueFromCache(cacheKey, tenantId); if (entry != null) { + if (LOG.isDebugEnabled()) { + LOG.debug(String.format("Cache entry found for authenticator %s.", authenticatorConfigName)); + } return entry.getAuthenticatorConfig(); } + if (LOG.isDebugEnabled()) { + LOG.debug(String.format( + "Cache entry not found for authenticator %s. Fetching from DB.", authenticatorConfigName)); + } UserDefinedLocalAuthenticatorConfig authenticatorConfig = authenticatorMgtFacade .getUserDefinedLocalAuthenticator(authenticatorConfigName, tenantId); + authenticatorCache.addToCache(cacheKey, new AuthenticatorCacheEntry(authenticatorConfig), tenantId); + if (LOG.isDebugEnabled()) { + LOG.debug(String.format( + "Entry fetched from DB for authenticator %s. Adding cache entry.", authenticatorConfigName)); + } return authenticatorConfig; } @@ -97,6 +117,9 @@ public void deleteUserDefinedLocalAuthenticator(String authenticatorConfigName, UserDefinedLocalAuthenticatorConfig authenticatorConfig, int tenantId) throws AuthenticatorMgtException { authenticatorCache.clearCacheEntry(new AuthenticatorCacheKey(authenticatorConfigName), tenantId); + if (LOG.isDebugEnabled()) { + LOG.debug(String.format("Delete cache entry of deleting authenticator %s.", authenticatorConfigName)); + } authenticatorMgtFacade.deleteUserDefinedLocalAuthenticator(authenticatorConfigName, authenticatorConfig, tenantId); } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/AuthenticatorMgtExceptionBuilder.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/AuthenticatorMgtExceptionBuilder.java index 2af2b74f3d81..7e5fd775ae89 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/AuthenticatorMgtExceptionBuilder.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/AuthenticatorMgtExceptionBuilder.java @@ -98,23 +98,25 @@ public enum AuthenticatorMgtError { "Error while updating authenticator in the system."), ERROR_WHILE_RETRIEVING_AUTHENTICATOR_BY_NAME("65003", "Error while retrieving authenticator.", "Error while retrieving authenticator in the system."), - ERROR_WHILE_DELETING_AUTHENTICATOR("65004", "Error while deleting authenticator.", + ERROR_WHILE_ALL_RETRIEVING_AUTHENTICATOR("65004", "Error while all retrieving authenticator.", + "Error while retrieving all authenticators in the system."), + ERROR_WHILE_DELETING_AUTHENTICATOR("65005", "Error while deleting authenticator.", "Error while deleting authenticator in the system."), - ERROR_CODE_INVALID_DEFINED_BY_AUTH_PROVIDED("65005", "Error while adding local authenticator.", + ERROR_CODE_INVALID_DEFINED_BY_AUTH_PROVIDED("65006", "Error while adding local authenticator.", "Only system defined authenticators are allowed to add via this method."), - ERROR_CODE_NO_AUTHENTICATOR_FOUND("65006", "No authenticator found.", + ERROR_CODE_NO_AUTHENTICATOR_FOUND("65007", "No authenticator found.", "No authenticator found by given authenticator name: %s."), - ERROR_CODE_NO_ACTION_ID_FOUND("65007", "No action id found.", + ERROR_CODE_NO_ACTION_ID_FOUND("65008", "No action id found.", "No action id found for the authenticator: %s."), - ERROR_CODE_ADDING_ENDPOINT_CONFIG("65008", "Error while adding endpoint configurations.", + ERROR_CODE_ADDING_ENDPOINT_CONFIG("65009", "Error while adding endpoint configurations.", "Error while adding endpoint configurations for the user defined local authenticator %s."), - ERROR_CODE_UPDATING_ENDPOINT_CONFIG("65009", "Error while updating endpoint configurations.", + ERROR_CODE_UPDATING_ENDPOINT_CONFIG("65010", "Error while updating endpoint configurations.", "Error while updating endpoint configurations for the user defined local authenticator %s."), - ERROR_CODE_RETRIEVING_ENDPOINT_CONFIG("65010", "Error while resolving endpoint configurations.", + ERROR_CODE_RETRIEVING_ENDPOINT_CONFIG("65011", "Error while resolving endpoint configurations.", "Error while retrieving endpoint configurations for the user defined local authenticator %s."), - ERROR_CODE_DELETING_ENDPOINT_CONFIG("65011", "Error while managing endpoint configurations.", + ERROR_CODE_DELETING_ENDPOINT_CONFIG("65012", "Error while managing endpoint configurations.", "Error while managing endpoint configurations for the user defined local authenticator %s."), - ERROR_CODE_HAVING_MULTIPLE_PROP("65012", "Multiple properties found", "Only actionId " + + ERROR_CODE_HAVING_MULTIPLE_PROP("65013", "Multiple properties found", "Only actionId " + "property is allowed for authenticator: %s."); private final String code; diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/IdentityApplicationConstants.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/IdentityApplicationConstants.java index 8bdbfc112044..655e4e0674c3 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/IdentityApplicationConstants.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/IdentityApplicationConstants.java @@ -167,6 +167,7 @@ private ConfigElements() { public static class Authenticator { public static final String ACTION_ID_PROPERTY = "actionId"; + public static final String DISPLAY_NAME = "displayName"; /** * OpenId authenticator constants. diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedAuthenticatorEndpointConfigManager.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedAuthenticatorEndpointConfigManager.java index 04fa9447c718..50d304aa53b6 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedAuthenticatorEndpointConfigManager.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/UserDefinedAuthenticatorEndpointConfigManager.java @@ -18,9 +18,12 @@ package org.wso2.carbon.identity.application.common.util; +import org.wso2.carbon.identity.action.management.exception.ActionMgtClientException; import org.wso2.carbon.identity.action.management.exception.ActionMgtException; import org.wso2.carbon.identity.action.management.model.Action; import org.wso2.carbon.identity.action.management.model.EndpointConfig; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtClientException; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtException; import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtServerException; import org.wso2.carbon.identity.application.common.internal.ApplicationCommonServiceDataHolder; import org.wso2.carbon.identity.application.common.model.Property; @@ -47,10 +50,10 @@ public class UserDefinedAuthenticatorEndpointConfigManager { * * @param config The Local application authenticator configuration. * @param tenantId The id of Tenant domain. - * @throws AuthenticatorMgtServerException If an error occurs while adding the action. + * @throws AuthenticatorMgtException If an error occurs while adding the action. */ public void addEndpointConfigurations(UserDefinedLocalAuthenticatorConfig config, int tenantId) - throws AuthenticatorMgtServerException { + throws AuthenticatorMgtException { try { Action action = ApplicationCommonServiceDataHolder.getInstance().getActionManagementService() @@ -62,7 +65,8 @@ public void addEndpointConfigurations(UserDefinedLocalAuthenticatorConfig config endpointProperty.setValue(action.getId()); config.setProperties(new Property[]{endpointProperty}); } catch (ActionMgtException e) { - throw buildServerException(AuthenticatorMgtError.ERROR_CODE_ADDING_ENDPOINT_CONFIG, e, config.getName()); + throw handleActionMgtException(AuthenticatorMgtError.ERROR_CODE_ADDING_ENDPOINT_CONFIG, + e, config.getName()); } } @@ -72,11 +76,11 @@ public void addEndpointConfigurations(UserDefinedLocalAuthenticatorConfig config * @param newConfig The Local application authenticator configuration to be updated. * @param oldConfig The current Local application authenticator configuration. * @param tenantId The id of Tenant domain. - * @throws AuthenticatorMgtServerException If an error occurs while updating associated action. + * @throws AuthenticatorMgtException If an error occurs while updating associated action. */ public void updateEndpointConfigurations(UserDefinedLocalAuthenticatorConfig newConfig, UserDefinedLocalAuthenticatorConfig oldConfig, int tenantId) - throws AuthenticatorMgtServerException { + throws AuthenticatorMgtException { String actionId = getActionIdFromProperty(oldConfig.getProperties(), oldConfig.getName()); try { @@ -87,7 +91,7 @@ public void updateEndpointConfigurations(UserDefinedLocalAuthenticatorConfig new IdentityTenantUtil.getTenantDomain(tenantId)); newConfig.setProperties(oldConfig.getProperties()); } catch (ActionMgtException e) { - throw buildServerException(AuthenticatorMgtError.ERROR_CODE_UPDATING_ENDPOINT_CONFIG, e, + throw handleActionMgtException(AuthenticatorMgtError.ERROR_CODE_UPDATING_ENDPOINT_CONFIG, e, actionId, oldConfig.getName()); } } @@ -98,10 +102,10 @@ public void updateEndpointConfigurations(UserDefinedLocalAuthenticatorConfig new * @param config The Local application authenticator configuration. * @param tenantId The id of Tenant domain. * @return Local authenticator with endpoint configurations resolved. - * @throws AuthenticatorMgtServerException If an error occurs retrieving updating associated action. + * @throws AuthenticatorMgtException If an error occurs retrieving updating associated action. */ public UserDefinedLocalAuthenticatorConfig resolveEndpointConfigurations(UserDefinedLocalAuthenticatorConfig config, - int tenantId) throws AuthenticatorMgtServerException { + int tenantId) throws AuthenticatorMgtException { if (config == null) { return null; @@ -116,7 +120,7 @@ public UserDefinedLocalAuthenticatorConfig resolveEndpointConfigurations(UserDef config.setEndpointConfig(buildUserDefinedAuthenticatorEndpointConfig(action.getEndpoint())); return config; } catch (ActionMgtException e) { - throw buildServerException(AuthenticatorMgtError.ERROR_CODE_RETRIEVING_ENDPOINT_CONFIG, e, + throw handleActionMgtException(AuthenticatorMgtError.ERROR_CODE_RETRIEVING_ENDPOINT_CONFIG, e, actionId, config.getName()); } } @@ -140,11 +144,10 @@ private UserDefinedAuthenticatorEndpointConfig buildUserDefinedAuthenticatorEndp * * @param config The Local application authenticator configuration. * @param tenantId The id of Tenant domain. - * - * @throws AuthenticatorMgtServerException If an error occurs while deleting associated action. + * @throws AuthenticatorMgtException If an error occurs while deleting associated action. */ public void deleteEndpointConfigurations(UserDefinedLocalAuthenticatorConfig config, int tenantId) throws - AuthenticatorMgtServerException { + AuthenticatorMgtException { String actionId = getActionIdFromProperty(config.getProperties(), config.getName()); try { @@ -153,7 +156,7 @@ public void deleteEndpointConfigurations(UserDefinedLocalAuthenticatorConfig con actionId, IdentityTenantUtil.getTenantDomain(tenantId)); } catch (ActionMgtException e) { - throw buildServerException(AuthenticatorMgtError.ERROR_CODE_DELETING_ENDPOINT_CONFIG, e, + throw handleActionMgtException(AuthenticatorMgtError.ERROR_CODE_DELETING_ENDPOINT_CONFIG, e, actionId, config.getName()); } } @@ -187,4 +190,17 @@ private String getActionIdFromProperty(Property[] properties, String authenticat .orElseThrow(() -> buildServerException(AuthenticatorMgtError.ERROR_CODE_NO_ACTION_ID_FOUND, authenticatorName)); } + + private static AuthenticatorMgtException handleActionMgtException(AuthenticatorMgtError authenticatorMgtError, + Throwable actionException, String... data) + throws AuthenticatorMgtException { + + if (actionException instanceof ActionMgtClientException) { + ActionMgtClientException error = (ActionMgtClientException) actionException; + throw new AuthenticatorMgtClientException( + authenticatorMgtError.getCode(), error.getMessage(), error.getDescription()); + } + + throw buildServerException(authenticatorMgtError, data); + } } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java index 088697fcadcb..f75199d6e85e 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/ApplicationAuthenticatorServiceTest.java @@ -24,12 +24,15 @@ import org.testng.annotations.BeforeClass; import org.testng.annotations.DataProvider; import org.testng.annotations.Test; -import org.wso2.carbon.identity.action.management.exception.ActionMgtException; +import org.wso2.carbon.identity.action.management.exception.ActionMgtClientException; +import org.wso2.carbon.identity.action.management.exception.ActionMgtServerException; import org.wso2.carbon.identity.action.management.model.Action; import org.wso2.carbon.identity.action.management.model.EndpointConfig; import org.wso2.carbon.identity.action.management.service.ActionManagementService; import org.wso2.carbon.identity.application.common.ApplicationAuthenticatorService; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtClientException; import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtException; +import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtServerException; import org.wso2.carbon.identity.application.common.exception.AuthenticatorMgtServerRuntimeException; import org.wso2.carbon.identity.application.common.internal.ApplicationCommonServiceDataHolder; import org.wso2.carbon.identity.application.common.model.LocalAuthenticatorConfig; @@ -176,7 +179,7 @@ public void testCreateUserDefinedLocalAuthenticatorWithBlankDisplayName() throws .addUserDefinedLocalAuthenticator(config, tenantDomain); } - @Test(priority = 3, expectedExceptions = AuthenticatorMgtException.class, + @Test(priority = 4, expectedExceptions = AuthenticatorMgtException.class, expectedExceptionsMessageRegExp = "Authenticator name is invalid.") public void testCreateUserDefinedLocalAuthenticatorWithInvalidName() throws AuthenticatorMgtException { @@ -185,21 +188,35 @@ public void testCreateUserDefinedLocalAuthenticatorWithInvalidName() throws Auth AuthenticationType.IDENTIFICATION), tenantDomain); } - @Test(priority = 4) - public void testAddIdPActionException() throws Exception { + @Test(priority = 5) + public void testAddIdPActionServerException() throws Exception { ActionManagementService actionManagementServiceForException = mock(ActionManagementService.class); when(actionManagementServiceForException.addAction(anyString(), any(), any())) - .thenThrow(ActionMgtException.class); + .thenThrow(ActionMgtServerException.class); ApplicationCommonServiceDataHolder.getInstance().setActionManagementService( actionManagementServiceForException); - assertThrows(AuthenticatorMgtException.class, () -> + assertThrows(AuthenticatorMgtServerException.class, () -> ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() .addUserDefinedLocalAuthenticator(authenticatorConfigForException, tenantDomain)); } - @Test(priority = 5) + @Test(priority = 6) + public void testAddIdPActionClientException() throws Exception { + + ActionManagementService actionManagementServiceForException = mock(ActionManagementService.class); + when(actionManagementServiceForException.addAction(anyString(), any(), any())) + .thenThrow(ActionMgtClientException.class); + ApplicationCommonServiceDataHolder.getInstance().setActionManagementService( + actionManagementServiceForException); + + assertThrows(AuthenticatorMgtClientException.class, () -> + ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() + .addUserDefinedLocalAuthenticator(authenticatorConfigForException, tenantDomain)); + } + + @Test(priority = 7) public void testAddLocalAuthenticator() { ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() @@ -208,7 +225,7 @@ public void testAddLocalAuthenticator() { .getLocalAuthenticatorByName(SYSTEM_AUTHENTICATOR_NAME)); } - @Test(priority = 6) + @Test(priority = 8) public void testAddLocalAuthenticatorWithRuntimeError() { AuthenticatorMgtServerRuntimeException exception = assertThrows(AuthenticatorMgtServerRuntimeException.class, @@ -218,7 +235,7 @@ public void testAddLocalAuthenticatorWithRuntimeError() { } - @Test(priority = 10) + @Test(priority = 9) public void testGetAllUserDefinedLocalAuthenticators() throws Exception { List authenticatorsList = ApplicationCommonServiceDataHolder.getInstance() @@ -257,12 +274,12 @@ public void testGetUserDefinedAuthenticatorWithActionException() throws Exceptio ActionManagementService actionManagementServiceForException = mock(ActionManagementService.class); when(actionManagementServiceForException.addAction(anyString(), any(), any())).thenReturn(action); when(actionManagementServiceForException.getActionByActionId(anyString(), any(), any())) - .thenThrow(ActionMgtException.class); + .thenThrow(ActionMgtServerException.class); ApplicationCommonServiceDataHolder.getInstance().setActionManagementService( actionManagementServiceForException); } - @Test(priority = 20, dataProvider = "authenticatorConfigToModify") + @Test(priority = 12, dataProvider = "authenticatorConfigToModify") public void testUpdateUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticatorConfig config) throws AuthenticatorMgtException { @@ -276,7 +293,7 @@ public void testUpdateUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticato Assert.assertEquals(updatedAuthenticator.getProperties().length, config.getProperties().length); } - @Test(priority = 21, expectedExceptions = AuthenticatorMgtException.class, + @Test(priority = 13, expectedExceptions = AuthenticatorMgtException.class, expectedExceptionsMessageRegExp = "No Authenticator found.") public void testUpdateUserDefinedLocalAuthenticatorWithNonExistingAuthenticator() throws AuthenticatorMgtException { @@ -284,17 +301,17 @@ public void testUpdateUserDefinedLocalAuthenticatorWithNonExistingAuthenticator( .updateUserDefinedLocalAuthenticator(nonExistAuthenticatorConfig, tenantDomain); } - @Test(priority = 22) + @Test(priority = 14) public void testUpdateIdPActionException() throws Exception { ActionManagementService actionManagementServiceForException = mock(ActionManagementService.class); when(actionManagementServiceForException.updateAction(any(), any(), any(), any())) - .thenThrow(ActionMgtException.class); + .thenThrow(ActionMgtServerException.class); when(actionManagementServiceForException.getActionByActionId(anyString(), any(), any())).thenReturn(action); ApplicationCommonServiceDataHolder.getInstance().setActionManagementService( actionManagementServiceForException); - assertThrows(AuthenticatorMgtException.class, () -> ApplicationCommonServiceDataHolder.getInstance() + assertThrows(AuthenticatorMgtServerException.class, () -> ApplicationCommonServiceDataHolder.getInstance() .getApplicationAuthenticatorService().updateUserDefinedLocalAuthenticator( authenticatorConfigForException, tenantDomain)); } @@ -309,7 +326,7 @@ public Object[][] authenticatorConfigToRetrieve() { }; } - @Test(priority = 27, dataProvider = "authenticatorConfigToRetrieve") + @Test(priority = 15, dataProvider = "authenticatorConfigToRetrieve") public void testGetUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticatorConfig configToBeRetrieved, UserDefinedLocalAuthenticatorConfig expectedConfig, String type) throws AuthenticatorMgtException { @@ -329,16 +346,17 @@ public void testGetUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticatorCo } } - @Test(priority = 40) + @Test(priority = 16) public void testDeleteUserDefinedLocalAuthenticatorWithActionException() throws Exception { ActionManagementService actionManagementServiceForException = mock(ActionManagementService.class); - doThrow(ActionMgtException.class).when(actionManagementServiceForException).deleteAction(any(), any(), any()); + doThrow(ActionMgtServerException.class) + .when(actionManagementServiceForException).deleteAction(any(), any(), any()); when(actionManagementServiceForException.getActionByActionId(anyString(), any(), any())).thenReturn(action); ApplicationCommonServiceDataHolder.getInstance() .setActionManagementService(actionManagementServiceForException); - assertThrows(AuthenticatorMgtException.class, () -> ApplicationCommonServiceDataHolder.getInstance(). + assertThrows(AuthenticatorMgtServerException.class, () -> ApplicationCommonServiceDataHolder.getInstance(). getApplicationAuthenticatorService().deleteUserDefinedLocalAuthenticator( authenticatorConfigForException.getName(), tenantDomain)); Assert.assertNotNull(ApplicationCommonServiceDataHolder.getInstance(). @@ -346,7 +364,7 @@ public void testDeleteUserDefinedLocalAuthenticatorWithActionException() throws authenticatorConfigForException.getName(), tenantDomain)); } - @Test(priority = 50, dataProvider = "authenticatorConfigToModify") + @Test(priority = 17, dataProvider = "authenticatorConfigToModify") public void testDeleteUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticatorConfig config) throws AuthenticatorMgtException { @@ -356,9 +374,10 @@ public void testDeleteUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticato .getLocalAuthenticatorByName(config.getName())); } - @Test(priority = 51) + @Test(priority = 18) public void testDeleteUserDefinedLocalAuthenticatorWithNonExistingAuthenticator() throws AuthenticatorMgtException { + // Assert that no exception is thrown when trying to delete a non-existing authenticator. ApplicationCommonServiceDataHolder.getInstance().getApplicationAuthenticatorService() .deleteUserDefinedLocalAuthenticator(nonExistAuthenticatorConfig.getName(), tenantDomain); } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/dao/AuthenticatorManagementDAOImplTest.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/dao/AuthenticatorManagementDAOImplTest.java index f2f06a88b27d..ef4b5ba57c49 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/dao/AuthenticatorManagementDAOImplTest.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/test/java/org/wso2/carbon/identity/application/common/model/test/dao/AuthenticatorManagementDAOImplTest.java @@ -105,7 +105,7 @@ public void testAddUserDefinedLocalAuthenticatorWithSQLException() { Assert.assertEquals(exception.getErrorCode(), ERROR_WHILE_ADDING_AUTHENTICATOR.getCode()); } - @Test(priority = 15) + @Test(priority = 3) public void testAddUserDefinedLocalAuthenticatorWithOutActionProperty() { authenticatorConfigForException.setProperties(new Property[0]); @@ -114,7 +114,7 @@ public void testAddUserDefinedLocalAuthenticatorWithOutActionProperty() { Assert.assertEquals(exception.getErrorCode(), ERROR_WHILE_ADDING_AUTHENTICATOR.getCode()); } - @Test(priority = 19) + @Test(priority = 4) public void testUpdateUserDefinedLocalAuthenticator() throws AuthenticatorMgtException { UserDefinedLocalAuthenticatorConfig updatedConfig = authenticatorManagementDAO @@ -128,7 +128,7 @@ public void testUpdateUserDefinedLocalAuthenticator() throws AuthenticatorMgtExc authenticatorConfig1 = authenticatorForUpdate; } - @Test(priority = 21) + @Test(priority = 5) public void testUpdateUserDefinedLocalAuthenticatorForException() { AuthenticatorMgtException exception = assertThrows(AuthenticatorMgtException.class, () -> @@ -137,7 +137,7 @@ public void testUpdateUserDefinedLocalAuthenticatorForException() { Assert.assertEquals(exception.getErrorCode(), ERROR_WHILE_UPDATING_AUTHENTICATOR.getCode()); } - @Test(dataProvider = "authenticatorConfig", priority = 31) + @Test(dataProvider = "authenticatorConfig", priority = 6) public void testGetUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticatorConfig config) throws AuthenticatorMgtException { @@ -150,7 +150,7 @@ public void testGetUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticatorCo Assert.assertEquals(retrievedConfig.getDefinedByType(), config.getDefinedByType()); } - @Test(priority = 41) + @Test(priority = 7) public void testGetNonExistingUserDefinedLocalAuthenticator() throws AuthenticatorMgtException { UserDefinedLocalAuthenticatorConfig config = authenticatorManagementDAO.getUserDefinedLocalAuthenticator( @@ -159,14 +159,14 @@ public void testGetNonExistingUserDefinedLocalAuthenticator() throws Authenticat Assert.assertNull(config); } - @Test(priority = 51) + @Test(priority = 8) public void testGetUserDefinedLocalAuthenticatorForNonExist() throws AuthenticatorMgtException { Assert.assertNull(authenticatorManagementDAO.getUserDefinedLocalAuthenticator( NON_EXIST_AUTHENTICATOR_NAME, tenantId)); } - @Test(dataProvider = "authenticatorConfig", priority = 134) + @Test(dataProvider = "authenticatorConfig", priority = 9) public void testDeleteUserDefinedLocalAuthenticator(UserDefinedLocalAuthenticatorConfig config) throws AuthenticatorMgtException { diff --git a/features/api-resource-mgt/org.wso2.carbon.identity.api.resource.mgt.server.feature/resources/system-api-resource.xml b/features/api-resource-mgt/org.wso2.carbon.identity.api.resource.mgt.server.feature/resources/system-api-resource.xml index da31c426930a..5043c3e091b8 100644 --- a/features/api-resource-mgt/org.wso2.carbon.identity.api.resource.mgt.server.feature/resources/system-api-resource.xml +++ b/features/api-resource-mgt/org.wso2.carbon.identity.api.resource.mgt.server.feature/resources/system-api-resource.xml @@ -1219,4 +1219,16 @@ description="View metadata for rule configuration"/> + + + + + + + diff --git a/features/api-resource-mgt/org.wso2.carbon.identity.api.resource.mgt.server.feature/resources/system-api-resource.xml.j2 b/features/api-resource-mgt/org.wso2.carbon.identity.api.resource.mgt.server.feature/resources/system-api-resource.xml.j2 index 9fba6a3582e6..e4e83cf56fac 100644 --- a/features/api-resource-mgt/org.wso2.carbon.identity.api.resource.mgt.server.feature/resources/system-api-resource.xml.j2 +++ b/features/api-resource-mgt/org.wso2.carbon.identity.api.resource.mgt.server.feature/resources/system-api-resource.xml.j2 @@ -1236,4 +1236,16 @@ description="View metadata for rule configuration"/> + + + + + + + diff --git a/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/identity.xml b/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/identity.xml index cb2727a4e620..f988cfe93302 100644 --- a/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/identity.xml +++ b/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/identity.xml @@ -2315,15 +2315,15 @@ internal_action_mgt_view - + /permission/admin/manage/custom_authenticator/create internal_custom_authenticator_create - + /permission/admin/manage/custom_authenticator/update internal_custom_authenticator_update - + /permission/admin/manage/custom_authenticator/delete internal_custom_authenticator_delete diff --git a/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/identity.xml.j2 b/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/identity.xml.j2 index 90e7d3aa010a..1fb47e66cb67 100644 --- a/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/identity.xml.j2 +++ b/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/identity.xml.j2 @@ -3574,15 +3574,15 @@ internal_action_mgt_view - + /permission/admin/manage/custom_authenticator/create internal_custom_authenticator_create - + /permission/admin/manage/custom_authenticator/update internal_custom_authenticator_update - + /permission/admin/manage/custom_authenticator/delete internal_custom_authenticator_delete diff --git a/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/resource-access-control-v2.xml b/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/resource-access-control-v2.xml index f6888d5371b0..89ce8f23d042 100644 --- a/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/resource-access-control-v2.xml +++ b/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/resource-access-control-v2.xml @@ -1208,13 +1208,13 @@ - + internal_custom_authenticator_create - + internal_custom_authenticator_update - + internal_custom_authenticator_delete diff --git a/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/resource-access-control-v2.xml.j2 b/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/resource-access-control-v2.xml.j2 index 13035ed3a86d..2afb969a8f7e 100644 --- a/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/resource-access-control-v2.xml.j2 +++ b/features/identity-core/org.wso2.carbon.identity.core.server.feature/resources/resource-access-control-v2.xml.j2 @@ -1272,13 +1272,13 @@ - + internal_custom_authenticator_create - + internal_custom_authenticator_update - + internal_custom_authenticator_delete From 493b17be2f4b2ba2fab3aa9913b193f137d4ef9a Mon Sep 17 00:00:00 2001 From: Thisara-Welmilla Date: Sun, 15 Dec 2024 10:35:56 +0530 Subject: [PATCH 11/15] Remove cross component transaction for add method. --- .../impl/AuthenticatorManagementFacade.java | 21 ++++++++----------- 1 file changed, 9 insertions(+), 12 deletions(-) diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java index ec8da806088d..dcafcddbf892 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java @@ -44,7 +44,7 @@ public class AuthenticatorManagementFacade implements AuthenticatorManagementDAO { private final AuthenticatorManagementDAO dao; - private UserDefinedAuthenticatorEndpointConfigManager endpointConfigManager = + private final UserDefinedAuthenticatorEndpointConfigManager endpointConfigManager = new UserDefinedAuthenticatorEndpointConfigManager(); public AuthenticatorManagementFacade(AuthenticatorManagementDAO dao) { @@ -65,18 +65,15 @@ public AuthenticatorManagementFacade(AuthenticatorManagementDAO dao) { public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( UserDefinedLocalAuthenticatorConfig authenticatorConfig, int tenantId) throws AuthenticatorMgtException { - - NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); + //TODO: Refer https://github.com/wso2-enterprise/asgardeo-product/issues/27910 + endpointConfigManager.addEndpointConfigurations(authenticatorConfig, tenantId); try { - return jdbcTemplate.withTransaction(template -> { - endpointConfigManager.addEndpointConfigurations(authenticatorConfig, tenantId); - validateAuthenticatorProperties(authenticatorConfig); - return endpointConfigManager.resolveEndpointConfigurations( - dao.addUserDefinedLocalAuthenticator(authenticatorConfig, tenantId), tenantId); - }); - } catch (TransactionException e) { - throw handleAuthenticatorMgtException(AuthenticatorMgtError.ERROR_WHILE_ADDING_AUTHENTICATOR, e, - authenticatorConfig.getName()); + validateAuthenticatorProperties(authenticatorConfig); + return endpointConfigManager.resolveEndpointConfigurations( + dao.addUserDefinedLocalAuthenticator(authenticatorConfig, tenantId), tenantId); + } catch (AuthenticatorMgtException e) { + endpointConfigManager.deleteEndpointConfigurations(authenticatorConfig, tenantId); + throw e; } } From 41f2eb1b30187eb90d4ec690a4f0f8bbe2d56338 Mon Sep 17 00:00:00 2001 From: Thisara-Welmilla Date: Mon, 16 Dec 2024 11:04:40 +0530 Subject: [PATCH 12/15] Improve dao layer. --- .../impl/AuthenticatorManagementDAOImpl.java | 113 ++++++++++-------- .../impl/AuthenticatorManagementFacade.java | 18 +-- 2 files changed, 73 insertions(+), 58 deletions(-) diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java index ed953197c3a5..a316ef72e8b8 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java @@ -19,7 +19,7 @@ package org.wso2.carbon.identity.application.common.dao.impl; import org.wso2.carbon.database.utils.jdbc.NamedJdbcTemplate; -import org.wso2.carbon.database.utils.jdbc.exceptions.DataAccessException; +import org.wso2.carbon.database.utils.jdbc.exceptions.TransactionException; import org.wso2.carbon.identity.application.common.constant.AuthenticatorMgtSQLConstants.Column; import org.wso2.carbon.identity.application.common.constant.AuthenticatorMgtSQLConstants.Query; import org.wso2.carbon.identity.application.common.dao.AuthenticatorManagementDAO; @@ -52,23 +52,24 @@ public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); try { - jdbcTemplate.executeInsert(Query.ADD_AUTHENTICATOR_SQL, - (statement -> { - statement.setString(Column.NAME, authenticatorConfig.getName()); - statement.setString(Column.DISPLAY_NAME, authenticatorConfig.getDisplayName()); - statement.setString(Column.DEFINED_BY, authenticatorConfig.getDefinedByType().toString()); - statement.setString(Column.AUTHENTICATION_TYPE, authenticatorConfig.getAuthenticationType() - .toString()); - statement.setInt(Column.IS_ENABLED, authenticatorConfig.isEnabled() ? 1 : 0); - statement.setString(Column.IDP_NAME, LOCAL_IDP_NAME); - statement.setInt(Column.TENANT_ID, tenantId); - }), null, false); + jdbcTemplate.withTransaction(template -> + jdbcTemplate.executeInsert(Query.ADD_AUTHENTICATOR_SQL, + (statement -> { + statement.setString(Column.NAME, authenticatorConfig.getName()); + statement.setString(Column.DISPLAY_NAME, authenticatorConfig.getDisplayName()); + statement.setString(Column.DEFINED_BY, authenticatorConfig.getDefinedByType().toString()); + statement.setString(Column.AUTHENTICATION_TYPE, authenticatorConfig.getAuthenticationType() + .toString()); + statement.setInt(Column.IS_ENABLED, authenticatorConfig.isEnabled() ? 1 : 0); + statement.setString(Column.IDP_NAME, LOCAL_IDP_NAME); + statement.setInt(Column.TENANT_ID, tenantId); + }), null, false)); int authenticatorConfigID = getAuthenticatorEntryId(authenticatorConfig.getName(), tenantId); addAuthenticatorProperty(authenticatorConfigID, authenticatorConfig.getProperties(), tenantId); return getUserDefinedLocalAuthenticatorByName(authenticatorConfig.getName(), tenantId); - } catch (DataAccessException e) { + } catch (TransactionException e) { throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_ADDING_AUTHENTICATOR, e); } } @@ -81,7 +82,8 @@ public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator( NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); try { - jdbcTemplate.executeUpdate(Query.UPDATE_AUTHENTICATOR_SQL, + jdbcTemplate.withTransaction(template -> { + jdbcTemplate.executeUpdate(Query.UPDATE_AUTHENTICATOR_SQL, statement -> { statement.setString(Column.DISPLAY_NAME, updatedAuthenticatorConfig.getDisplayName()); statement.setInt(Column.IS_ENABLED, updatedAuthenticatorConfig.isEnabled() ? 1 : 0); @@ -89,9 +91,11 @@ public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator( statement.setInt(Column.TENANT_ID, tenantId); statement.executeUpdate(); }); + return null; + }); return getUserDefinedLocalAuthenticatorByName(updatedAuthenticatorConfig.getName(), tenantId); - } catch (DataAccessException e) { + } catch (TransactionException e) { throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_UPDATING_AUTHENTICATOR, e); } } @@ -102,7 +106,7 @@ public UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator( try { return getUserDefinedLocalAuthenticatorByName(authenticatorConfigName, tenantId); - } catch (DataAccessException e) { + } catch (TransactionException e) { throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_RETRIEVING_AUTHENTICATOR_BY_NAME, e); } } @@ -114,7 +118,8 @@ public List getAllUserDefinedLocalAuthentic List allUserDefinedLocalConfigs = new ArrayList<>(); try { NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); - jdbcTemplate.executeQuery(Query.GET_ALL_USER_DEFINED_AUTHENTICATOR_SQL, + jdbcTemplate.withTransaction(template -> + jdbcTemplate.executeQuery(Query.GET_ALL_USER_DEFINED_AUTHENTICATOR_SQL, (resultSet, rowNumber) -> { UserDefinedLocalAuthenticatorConfig config = getLocalAuthenticatorConfigBasedOnType( resultSet.getString(Column.AUTHENTICATION_TYPE)); @@ -128,14 +133,14 @@ public List getAllUserDefinedLocalAuthentic statement -> { statement.setString(Column.DEFINED_BY, DefinedByType.USER.toString()); statement.setInt(Column.TENANT_ID, tenantId); - }); + })); for (UserDefinedLocalAuthenticatorConfig retrievedConfigs: allUserDefinedLocalConfigs) { int authenticatorConfigID = getAuthenticatorEntryId(retrievedConfigs.getName(), tenantId); retrievedConfigs.setProperties(getAuthenticatorProperties(authenticatorConfigID, tenantId)); } return allUserDefinedLocalConfigs; - } catch (DataAccessException e) { + } catch (TransactionException e) { throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_RETRIEVING_AUTHENTICATOR_BY_NAME, e); } } @@ -146,22 +151,26 @@ public void deleteUserDefinedLocalAuthenticator(String authenticatorConfigName, NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); try { - jdbcTemplate.executeUpdate(Query.DELETE_AUTHENTICATOR_SQL, - statement -> { - statement.setString(Column.NAME, authenticatorConfigName); - statement.setInt(Column.TENANT_ID, tenantId); - statement.executeUpdate(); - }); - } catch (DataAccessException e) { + jdbcTemplate.withTransaction(template -> { + jdbcTemplate.executeUpdate(Query.DELETE_AUTHENTICATOR_SQL, + statement -> { + statement.setString(Column.NAME, authenticatorConfigName); + statement.setInt(Column.TENANT_ID, tenantId); + statement.executeUpdate(); + }); + return null; + }); + } catch (TransactionException e) { throw buildServerException(AuthenticatorMgtError.ERROR_WHILE_DELETING_AUTHENTICATOR, e); } } private UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticatorByName(String authenticatorConfigName, - int tenantId) throws AuthenticatorMgtServerException, DataAccessException { + int tenantId) throws AuthenticatorMgtServerException, TransactionException { NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); - UserDefinedLocalAuthenticatorConfig authConfig = jdbcTemplate.fetchSingleRecord(Query.GET_AUTHENTICATOR_SQL, + UserDefinedLocalAuthenticatorConfig authConfig = jdbcTemplate.withTransaction(template -> + template.fetchSingleRecord(Query.GET_AUTHENTICATOR_SQL, (resultSet, rowNumber) -> { UserDefinedLocalAuthenticatorConfig config = getLocalAuthenticatorConfigBasedOnType( resultSet.getString(Column.AUTHENTICATION_TYPE)); @@ -175,7 +184,7 @@ private UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticatorByNa statement.setString(Column.NAME, authenticatorConfigName); statement.setInt(Column.TENANT_ID, tenantId); statement.setString(Column.DEFINED_BY, DefinedByType.USER.toString()); - }); + })); if (authConfig == null) { return null; @@ -183,7 +192,8 @@ private UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticatorByNa int authenticatorConfigID = getAuthenticatorEntryId(authenticatorConfigName, tenantId); List properties = new ArrayList<>(); - jdbcTemplate.fetchSingleRecord(Query.GET_AUTHENTICATOR_PROP_SQL, + jdbcTemplate.withTransaction(template -> + template.fetchSingleRecord(Query.GET_AUTHENTICATOR_PROP_SQL, (resultSet, rowNumber) -> { Property property = new Property(); property.setName(resultSet.getString(Column.PROPERTY_KEY)); @@ -195,7 +205,7 @@ private UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticatorByNa statementProp -> { statementProp.setInt(Column.AUTHENTICATOR_ID, authenticatorConfigID); statementProp.setInt(Column.TENANT_ID, tenantId); - }); + })); authConfig.setProperties(properties.toArray(new Property[0])); return authConfig; } @@ -209,15 +219,16 @@ private UserDefinedLocalAuthenticatorConfig getLocalAuthenticatorConfigBasedOnTy } private int getAuthenticatorEntryId(String authenticatorConfigName, int tenantId) - throws AuthenticatorMgtServerException, DataAccessException { + throws AuthenticatorMgtServerException, TransactionException { NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); - int id = jdbcTemplate.fetchSingleRecord(Query.GET_AUTHENTICATOR_ID_SQL, - (resultSet, rowNumber) -> resultSet.getInt(Column.ID), - statement -> { - statement.setString(Column.NAME, authenticatorConfigName); - statement.setInt(Column.TENANT_ID, tenantId); - }); + int id = jdbcTemplate.withTransaction(template -> + jdbcTemplate.fetchSingleRecord(Query.GET_AUTHENTICATOR_ID_SQL, + (resultSet, rowNumber) -> resultSet.getInt(Column.ID), + statement -> { + statement.setString(Column.NAME, authenticatorConfigName); + statement.setInt(Column.TENANT_ID, tenantId); + })); if (id != 0) { return id; @@ -227,25 +238,27 @@ private int getAuthenticatorEntryId(String authenticatorConfigName, int tenantId } private void addAuthenticatorProperty(int authenticatorConfigID, Property[] properties, int tenantId) - throws DataAccessException { + throws TransactionException { Property prop = properties[0]; NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); - jdbcTemplate.executeInsert(Query.ADD_AUTHENTICATOR_PROP_SQL, - (statementProp -> { - statementProp.setInt(Column.AUTHENTICATOR_ID, authenticatorConfigID); - statementProp.setInt(Column.TENANT_ID, tenantId); - statementProp.setString(Column.PROPERTY_KEY, prop.getName()); - statementProp.setString(Column.PROPERTY_VALUE, prop.getValue()); - statementProp.setString(Column.IS_SECRET, IS_FALSE_VALUE); - }), null, false); + jdbcTemplate.withTransaction(template -> + template.executeInsert(Query.ADD_AUTHENTICATOR_PROP_SQL, + (statementProp -> { + statementProp.setInt(Column.AUTHENTICATOR_ID, authenticatorConfigID); + statementProp.setInt(Column.TENANT_ID, tenantId); + statementProp.setString(Column.PROPERTY_KEY, prop.getName()); + statementProp.setString(Column.PROPERTY_VALUE, prop.getValue()); + statementProp.setString(Column.IS_SECRET, IS_FALSE_VALUE); + }), null, false)); } - private Property[] getAuthenticatorProperties(int authenticatorConfigID, int tenantId) throws DataAccessException { + private Property[] getAuthenticatorProperties(int authenticatorConfigID, int tenantId) throws TransactionException { List properties = new ArrayList<>(); NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); - jdbcTemplate.executeQuery(Query.GET_AUTHENTICATOR_PROP_SQL, + jdbcTemplate.withTransaction(template -> + jdbcTemplate.executeQuery(Query.GET_AUTHENTICATOR_PROP_SQL, (resultSet, rowNumber) -> { Property property = new Property(); property.setName(resultSet.getString(Column.PROPERTY_KEY)); @@ -257,7 +270,7 @@ private Property[] getAuthenticatorProperties(int authenticatorConfigID, int ten statementProp -> { statementProp.setInt(Column.AUTHENTICATOR_ID, authenticatorConfigID); statementProp.setInt(Column.TENANT_ID, tenantId); - }); + })); return properties.toArray(new Property[0]); } } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java index dcafcddbf892..62d3c8949509 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java @@ -65,15 +65,17 @@ public AuthenticatorManagementFacade(AuthenticatorManagementDAO dao) { public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( UserDefinedLocalAuthenticatorConfig authenticatorConfig, int tenantId) throws AuthenticatorMgtException { - //TODO: Refer https://github.com/wso2-enterprise/asgardeo-product/issues/27910 - endpointConfigManager.addEndpointConfigurations(authenticatorConfig, tenantId); + NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); try { - validateAuthenticatorProperties(authenticatorConfig); - return endpointConfigManager.resolveEndpointConfigurations( - dao.addUserDefinedLocalAuthenticator(authenticatorConfig, tenantId), tenantId); - } catch (AuthenticatorMgtException e) { - endpointConfigManager.deleteEndpointConfigurations(authenticatorConfig, tenantId); - throw e; + return jdbcTemplate.withTransaction(template -> { + endpointConfigManager.addEndpointConfigurations(authenticatorConfig, tenantId); + validateAuthenticatorProperties(authenticatorConfig); + return endpointConfigManager.resolveEndpointConfigurations( + dao.addUserDefinedLocalAuthenticator(authenticatorConfig, tenantId), tenantId); + }); + } catch (TransactionException e) { + throw handleAuthenticatorMgtException(AuthenticatorMgtError.ERROR_WHILE_UPDATING_AUTHENTICATOR, e, + authenticatorConfig.getName()); } } From b4c72152b306187802582076d1b8ee089a419804 Mon Sep 17 00:00:00 2001 From: Thisara-Welmilla Date: Mon, 16 Dec 2024 14:15:26 +0530 Subject: [PATCH 13/15] Address comments --- .../impl/AuthenticatorManagementDAOImpl.java | 118 ++++++++---------- 1 file changed, 54 insertions(+), 64 deletions(-) diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java index a316ef72e8b8..f6807c2a742e 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java @@ -33,7 +33,9 @@ import org.wso2.carbon.identity.core.util.IdentityDatabaseUtil; import java.util.ArrayList; +import java.util.HashMap; import java.util.List; +import java.util.Map; import static org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.buildServerException; @@ -52,20 +54,22 @@ public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); try { - jdbcTemplate.withTransaction(template -> - jdbcTemplate.executeInsert(Query.ADD_AUTHENTICATOR_SQL, - (statement -> { + int authenticatorConfigID = jdbcTemplate.withTransaction(template -> + template.executeInsert(Query.ADD_AUTHENTICATOR_SQL, + statement -> { statement.setString(Column.NAME, authenticatorConfig.getName()); statement.setString(Column.DISPLAY_NAME, authenticatorConfig.getDisplayName()); statement.setString(Column.DEFINED_BY, authenticatorConfig.getDefinedByType().toString()); statement.setString(Column.AUTHENTICATION_TYPE, authenticatorConfig.getAuthenticationType() .toString()); - statement.setInt(Column.IS_ENABLED, authenticatorConfig.isEnabled() ? 1 : 0); + statement.setString(Column.IS_ENABLED, String.valueOf(authenticatorConfig.isEnabled() ? 1 : 0)); statement.setString(Column.IDP_NAME, LOCAL_IDP_NAME); statement.setInt(Column.TENANT_ID, tenantId); - }), null, false)); + }, null, true)); - int authenticatorConfigID = getAuthenticatorEntryId(authenticatorConfig.getName(), tenantId); + if (authenticatorConfigID == 0) { + getAuthenticatorEntryId(authenticatorConfig.getName(), tenantId); + } addAuthenticatorProperty(authenticatorConfigID, authenticatorConfig.getProperties(), tenantId); return getUserDefinedLocalAuthenticatorByName(authenticatorConfig.getName(), tenantId); @@ -83,14 +87,14 @@ public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator( NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); try { jdbcTemplate.withTransaction(template -> { - jdbcTemplate.executeUpdate(Query.UPDATE_AUTHENTICATOR_SQL, - statement -> { - statement.setString(Column.DISPLAY_NAME, updatedAuthenticatorConfig.getDisplayName()); - statement.setInt(Column.IS_ENABLED, updatedAuthenticatorConfig.isEnabled() ? 1 : 0); - statement.setString(Column.NAME, existingAuthenticatorConfig.getName()); - statement.setInt(Column.TENANT_ID, tenantId); - statement.executeUpdate(); - }); + template.executeUpdate(Query.UPDATE_AUTHENTICATOR_SQL, + statement -> { + statement.setString(Column.DISPLAY_NAME, updatedAuthenticatorConfig.getDisplayName()); + statement.setString(Column.IS_ENABLED, + String.valueOf(updatedAuthenticatorConfig.isEnabled() ? 1 : 0)); + statement.setString(Column.NAME, existingAuthenticatorConfig.getName()); + statement.setInt(Column.TENANT_ID, tenantId); + }); return null; }); @@ -115,11 +119,12 @@ public UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticator( public List getAllUserDefinedLocalAuthenticators(int tenantId) throws AuthenticatorMgtException { - List allUserDefinedLocalConfigs = new ArrayList<>(); try { NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); - jdbcTemplate.withTransaction(template -> - jdbcTemplate.executeQuery(Query.GET_ALL_USER_DEFINED_AUTHENTICATOR_SQL, + HashMap authenticatorConfigMap = new HashMap<>(); + List allUserDefinedLocalConfigs = new ArrayList<>(); + jdbcTemplate.withTransaction( + template -> template.executeQuery(Query.GET_ALL_USER_DEFINED_AUTHENTICATOR_SQL, (resultSet, rowNumber) -> { UserDefinedLocalAuthenticatorConfig config = getLocalAuthenticatorConfigBasedOnType( resultSet.getString(Column.AUTHENTICATION_TYPE)); @@ -127,17 +132,17 @@ public List getAllUserDefinedLocalAuthentic config.setDisplayName(resultSet.getString(Column.DISPLAY_NAME)); config.setEnabled(resultSet.getString(Column.IS_ENABLED).equals(IS_TRUE_VALUE)); config.setDefinedByType(DefinedByType.valueOf(resultSet.getString(Column.DEFINED_BY))); - allUserDefinedLocalConfigs.add(config); - return null; + return authenticatorConfigMap.put(resultSet.getInt(Column.ID), config); }, statement -> { statement.setString(Column.DEFINED_BY, DefinedByType.USER.toString()); statement.setInt(Column.TENANT_ID, tenantId); })); - for (UserDefinedLocalAuthenticatorConfig retrievedConfigs: allUserDefinedLocalConfigs) { - int authenticatorConfigID = getAuthenticatorEntryId(retrievedConfigs.getName(), tenantId); - retrievedConfigs.setProperties(getAuthenticatorProperties(authenticatorConfigID, tenantId)); + for (Map.Entry entry: authenticatorConfigMap.entrySet()) { + UserDefinedLocalAuthenticatorConfig retrievedConfigs = entry.getValue(); + retrievedConfigs.setProperties(getAuthenticatorProperties(entry.getKey(), tenantId)); + allUserDefinedLocalConfigs.add(retrievedConfigs); } return allUserDefinedLocalConfigs; } catch (TransactionException e) { @@ -152,12 +157,12 @@ public void deleteUserDefinedLocalAuthenticator(String authenticatorConfigName, NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); try { jdbcTemplate.withTransaction(template -> { - jdbcTemplate.executeUpdate(Query.DELETE_AUTHENTICATOR_SQL, - statement -> { - statement.setString(Column.NAME, authenticatorConfigName); - statement.setInt(Column.TENANT_ID, tenantId); - statement.executeUpdate(); - }); + template.executeUpdate(Query.DELETE_AUTHENTICATOR_SQL, + statement -> { + statement.setString(Column.NAME, authenticatorConfigName); + statement.setInt(Column.TENANT_ID, tenantId); + statement.executeUpdate(); + }); return null; }); } catch (TransactionException e) { @@ -169,7 +174,9 @@ private UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticatorByNa int tenantId) throws AuthenticatorMgtServerException, TransactionException { NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); - UserDefinedLocalAuthenticatorConfig authConfig = jdbcTemplate.withTransaction(template -> + UserDefinedLocalAuthenticatorConfig retrievedConfigs = null; + HashMap authenticatorConfigMap = new HashMap<>(); + jdbcTemplate.withTransaction(template -> template.fetchSingleRecord(Query.GET_AUTHENTICATOR_SQL, (resultSet, rowNumber) -> { UserDefinedLocalAuthenticatorConfig config = getLocalAuthenticatorConfigBasedOnType( @@ -178,7 +185,7 @@ private UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticatorByNa config.setDisplayName(resultSet.getString(Column.DISPLAY_NAME)); config.setEnabled(resultSet.getString(Column.IS_ENABLED).equals(IS_TRUE_VALUE)); config.setDefinedByType(DefinedByType.USER); - return config; + return authenticatorConfigMap.put(resultSet.getInt(Column.ID), config); }, statement -> { statement.setString(Column.NAME, authenticatorConfigName); @@ -186,28 +193,13 @@ private UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticatorByNa statement.setString(Column.DEFINED_BY, DefinedByType.USER.toString()); })); - if (authConfig == null) { - return null; + for (Map.Entry entry: authenticatorConfigMap.entrySet()) { + retrievedConfigs = entry.getValue(); + retrievedConfigs.setProperties(getAuthenticatorProperties(entry.getKey(), tenantId)); + break; } - int authenticatorConfigID = getAuthenticatorEntryId(authenticatorConfigName, tenantId); - List properties = new ArrayList<>(); - jdbcTemplate.withTransaction(template -> - template.fetchSingleRecord(Query.GET_AUTHENTICATOR_PROP_SQL, - (resultSet, rowNumber) -> { - Property property = new Property(); - property.setName(resultSet.getString(Column.PROPERTY_KEY)); - property.setValue(resultSet.getString(Column.PROPERTY_VALUE)); - property.setConfidential(false); - properties.add(property); - return null; - }, - statementProp -> { - statementProp.setInt(Column.AUTHENTICATOR_ID, authenticatorConfigID); - statementProp.setInt(Column.TENANT_ID, tenantId); - })); - authConfig.setProperties(properties.toArray(new Property[0])); - return authConfig; + return retrievedConfigs; } private UserDefinedLocalAuthenticatorConfig getLocalAuthenticatorConfigBasedOnType(String authenticationType) { @@ -223,12 +215,12 @@ private int getAuthenticatorEntryId(String authenticatorConfigName, int tenantId NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); int id = jdbcTemplate.withTransaction(template -> - jdbcTemplate.fetchSingleRecord(Query.GET_AUTHENTICATOR_ID_SQL, - (resultSet, rowNumber) -> resultSet.getInt(Column.ID), - statement -> { - statement.setString(Column.NAME, authenticatorConfigName); - statement.setInt(Column.TENANT_ID, tenantId); - })); + template.fetchSingleRecord(Query.GET_AUTHENTICATOR_ID_SQL, + (resultSet, rowNumber) -> resultSet.getInt(Column.ID), + statement -> { + statement.setString(Column.NAME, authenticatorConfigName); + statement.setInt(Column.TENANT_ID, tenantId); + })); if (id != 0) { return id; @@ -243,29 +235,27 @@ private void addAuthenticatorProperty(int authenticatorConfigID, Property[] prop Property prop = properties[0]; NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); jdbcTemplate.withTransaction(template -> - template.executeInsert(Query.ADD_AUTHENTICATOR_PROP_SQL, - (statementProp -> { + template.executeInsert(Query.ADD_AUTHENTICATOR_PROP_SQL, + statementProp -> { statementProp.setInt(Column.AUTHENTICATOR_ID, authenticatorConfigID); statementProp.setInt(Column.TENANT_ID, tenantId); statementProp.setString(Column.PROPERTY_KEY, prop.getName()); statementProp.setString(Column.PROPERTY_VALUE, prop.getValue()); statementProp.setString(Column.IS_SECRET, IS_FALSE_VALUE); - }), null, false)); + }, null, false)); } private Property[] getAuthenticatorProperties(int authenticatorConfigID, int tenantId) throws TransactionException { - List properties = new ArrayList<>(); NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); - jdbcTemplate.withTransaction(template -> - jdbcTemplate.executeQuery(Query.GET_AUTHENTICATOR_PROP_SQL, + List properties = jdbcTemplate.withTransaction(template -> + template.executeQuery(Query.GET_AUTHENTICATOR_PROP_SQL, (resultSet, rowNumber) -> { Property property = new Property(); property.setName(resultSet.getString(Column.PROPERTY_KEY)); property.setValue(resultSet.getString(Column.PROPERTY_VALUE)); property.setConfidential(false); - properties.add(property); - return null; + return property; }, statementProp -> { statementProp.setInt(Column.AUTHENTICATOR_ID, authenticatorConfigID); From 7dd69e36ab4f7451b447aa1dfac72b50953a78c5 Mon Sep 17 00:00:00 2001 From: Thisara-Welmilla Date: Mon, 16 Dec 2024 16:48:15 +0530 Subject: [PATCH 14/15] Address comments --- .../impl/AuthenticatorManagementDAOImpl.java | 61 ++++++++++++------- .../impl/AuthenticatorManagementFacade.java | 1 + .../AuthenticatorMgtExceptionBuilder.java | 4 +- 3 files changed, 43 insertions(+), 23 deletions(-) diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java index f6807c2a742e..797a7c218a05 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java @@ -33,9 +33,7 @@ import org.wso2.carbon.identity.core.util.IdentityDatabaseUtil; import java.util.ArrayList; -import java.util.HashMap; import java.util.List; -import java.util.Map; import static org.wso2.carbon.identity.application.common.util.AuthenticatorMgtExceptionBuilder.buildServerException; @@ -62,13 +60,14 @@ public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( statement.setString(Column.DEFINED_BY, authenticatorConfig.getDefinedByType().toString()); statement.setString(Column.AUTHENTICATION_TYPE, authenticatorConfig.getAuthenticationType() .toString()); - statement.setString(Column.IS_ENABLED, String.valueOf(authenticatorConfig.isEnabled() ? 1 : 0)); + statement.setString(Column.IS_ENABLED, + authenticatorConfig.isEnabled() ? IS_TRUE_VALUE : IS_FALSE_VALUE); statement.setString(Column.IDP_NAME, LOCAL_IDP_NAME); statement.setInt(Column.TENANT_ID, tenantId); }, null, true)); if (authenticatorConfigID == 0) { - getAuthenticatorEntryId(authenticatorConfig.getName(), tenantId); + authenticatorConfigID = getAuthenticatorEntryId(authenticatorConfig.getName(), tenantId); } addAuthenticatorProperty(authenticatorConfigID, authenticatorConfig.getProperties(), tenantId); @@ -91,7 +90,7 @@ public UserDefinedLocalAuthenticatorConfig updateUserDefinedLocalAuthenticator( statement -> { statement.setString(Column.DISPLAY_NAME, updatedAuthenticatorConfig.getDisplayName()); statement.setString(Column.IS_ENABLED, - String.valueOf(updatedAuthenticatorConfig.isEnabled() ? 1 : 0)); + updatedAuthenticatorConfig.isEnabled() ? IS_TRUE_VALUE : IS_FALSE_VALUE); statement.setString(Column.NAME, existingAuthenticatorConfig.getName()); statement.setInt(Column.TENANT_ID, tenantId); }); @@ -121,9 +120,8 @@ public List getAllUserDefinedLocalAuthentic try { NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); - HashMap authenticatorConfigMap = new HashMap<>(); List allUserDefinedLocalConfigs = new ArrayList<>(); - jdbcTemplate.withTransaction( + List configDaoModels = jdbcTemplate.withTransaction( template -> template.executeQuery(Query.GET_ALL_USER_DEFINED_AUTHENTICATOR_SQL, (resultSet, rowNumber) -> { UserDefinedLocalAuthenticatorConfig config = getLocalAuthenticatorConfigBasedOnType( @@ -132,16 +130,16 @@ public List getAllUserDefinedLocalAuthentic config.setDisplayName(resultSet.getString(Column.DISPLAY_NAME)); config.setEnabled(resultSet.getString(Column.IS_ENABLED).equals(IS_TRUE_VALUE)); config.setDefinedByType(DefinedByType.valueOf(resultSet.getString(Column.DEFINED_BY))); - return authenticatorConfigMap.put(resultSet.getInt(Column.ID), config); + return new AuthenticatorConfigDaoModel(resultSet.getInt(Column.ID), config); }, statement -> { statement.setString(Column.DEFINED_BY, DefinedByType.USER.toString()); statement.setInt(Column.TENANT_ID, tenantId); })); - for (Map.Entry entry: authenticatorConfigMap.entrySet()) { - UserDefinedLocalAuthenticatorConfig retrievedConfigs = entry.getValue(); - retrievedConfigs.setProperties(getAuthenticatorProperties(entry.getKey(), tenantId)); + for (AuthenticatorConfigDaoModel config: configDaoModels) { + UserDefinedLocalAuthenticatorConfig retrievedConfigs = config.getConfig(); + retrievedConfigs.setProperties(getAuthenticatorProperties(config.getEntryId(), tenantId)); allUserDefinedLocalConfigs.add(retrievedConfigs); } return allUserDefinedLocalConfigs; @@ -171,12 +169,10 @@ public void deleteUserDefinedLocalAuthenticator(String authenticatorConfigName, } private UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticatorByName(String authenticatorConfigName, - int tenantId) throws AuthenticatorMgtServerException, TransactionException { + int tenantId) throws TransactionException { NamedJdbcTemplate jdbcTemplate = new NamedJdbcTemplate(IdentityDatabaseUtil.getDataSource()); - UserDefinedLocalAuthenticatorConfig retrievedConfigs = null; - HashMap authenticatorConfigMap = new HashMap<>(); - jdbcTemplate.withTransaction(template -> + AuthenticatorConfigDaoModel configDaoModel = jdbcTemplate.withTransaction(template -> template.fetchSingleRecord(Query.GET_AUTHENTICATOR_SQL, (resultSet, rowNumber) -> { UserDefinedLocalAuthenticatorConfig config = getLocalAuthenticatorConfigBasedOnType( @@ -185,7 +181,7 @@ private UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticatorByNa config.setDisplayName(resultSet.getString(Column.DISPLAY_NAME)); config.setEnabled(resultSet.getString(Column.IS_ENABLED).equals(IS_TRUE_VALUE)); config.setDefinedByType(DefinedByType.USER); - return authenticatorConfigMap.put(resultSet.getInt(Column.ID), config); + return new AuthenticatorConfigDaoModel(resultSet.getInt(Column.ID), config); }, statement -> { statement.setString(Column.NAME, authenticatorConfigName); @@ -193,13 +189,13 @@ private UserDefinedLocalAuthenticatorConfig getUserDefinedLocalAuthenticatorByNa statement.setString(Column.DEFINED_BY, DefinedByType.USER.toString()); })); - for (Map.Entry entry: authenticatorConfigMap.entrySet()) { - retrievedConfigs = entry.getValue(); - retrievedConfigs.setProperties(getAuthenticatorProperties(entry.getKey(), tenantId)); - break; + if (configDaoModel == null) { + return null; } - return retrievedConfigs; + UserDefinedLocalAuthenticatorConfig config = configDaoModel.getConfig(); + config.setProperties(getAuthenticatorProperties(configDaoModel.getEntryId(), tenantId)); + return config; } private UserDefinedLocalAuthenticatorConfig getLocalAuthenticatorConfigBasedOnType(String authenticationType) { @@ -263,4 +259,27 @@ private Property[] getAuthenticatorProperties(int authenticatorConfigID, int ten })); return properties.toArray(new Property[0]); } + + /** + * This class represents the user defined local authenticator configuration with entry id from DAO. + */ + private static class AuthenticatorConfigDaoModel { + + private final int entryId; + private final UserDefinedLocalAuthenticatorConfig config; + + private AuthenticatorConfigDaoModel(int entryId, UserDefinedLocalAuthenticatorConfig config) { + this.entryId = entryId; + this.config = config; + } + + public int getEntryId() { + return entryId; + } + + public UserDefinedLocalAuthenticatorConfig getConfig() { + return config; + } + } + } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java index 62d3c8949509..cd182863ec43 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementFacade.java @@ -151,6 +151,7 @@ public List getAllUserDefinedLocalAuthentic return jdbcTemplate.withTransaction(template -> { List configList = dao.getAllUserDefinedLocalAuthenticators(tenantId); + // TODO: Utilize a batch operation once issue:https://github.com/wso2/product-is/issues/21783 is done. for (UserDefinedLocalAuthenticatorConfig config : configList) { endpointConfigManager.resolveEndpointConfigurations(config, tenantId); } diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/AuthenticatorMgtExceptionBuilder.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/AuthenticatorMgtExceptionBuilder.java index 7e5fd775ae89..eb32b47d8d22 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/AuthenticatorMgtExceptionBuilder.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/util/AuthenticatorMgtExceptionBuilder.java @@ -82,8 +82,8 @@ public enum AuthenticatorMgtError { // Client errors. ERROR_NOT_FOUND_AUTHENTICATOR("60001", "No Authenticator found.", "No Authenticator found by given authenticator name: %s."), - ERROR_OP_ON_SYSTEM_AUTHENTICATOR("60002", "No operations allowed on system authenticators.", - "Do not allow to perform any operation on system defined authenticator: %s."), + ERROR_OPERATION_ALLOWED_FOR_SYSTEM_AUTHENTICATOR("60002", "No operations allowed on system " + + "authenticators.", "Do not allow to perform any operation on system defined authenticator: %s."), ERROR_AUTHENTICATOR_ALREADY_EXIST("60003", "The authenticator already exists.", "The authenticator already exists for the given name: %s."), ERROR_INVALID_AUTHENTICATOR_NAME("60004", "Authenticator name is invalid.", From be755b7202455e1dc7bf61f60562b2917b94c060 Mon Sep 17 00:00:00 2001 From: Thisara-Welmilla Date: Mon, 16 Dec 2024 19:06:20 +0530 Subject: [PATCH 15/15] Address comments --- .../common/dao/impl/AuthenticatorManagementDAOImpl.java | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java index 797a7c218a05..e04a7f860487 100644 --- a/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java +++ b/components/application-mgt/org.wso2.carbon.identity.application.common/src/main/java/org/wso2/carbon/identity/application/common/dao/impl/AuthenticatorManagementDAOImpl.java @@ -42,9 +42,9 @@ */ public class AuthenticatorManagementDAOImpl implements AuthenticatorManagementDAO { - public static final String IS_TRUE_VALUE = "1"; - public static final String IS_FALSE_VALUE = "0"; - public static final String LOCAL_IDP_NAME = "LOCAL"; + private static final String IS_TRUE_VALUE = "1"; + private static final String IS_FALSE_VALUE = "0"; + private static final String LOCAL_IDP_NAME = "LOCAL"; @Override public UserDefinedLocalAuthenticatorConfig addUserDefinedLocalAuthenticator( @@ -281,5 +281,4 @@ public UserDefinedLocalAuthenticatorConfig getConfig() { return config; } } - }