diff --git a/api/src/org/apache/cloudstack/api/command/admin/config/ListCfgsByCmd.java b/api/src/org/apache/cloudstack/api/command/admin/config/ListCfgsByCmd.java
index 8f71f48470e..80ebaf43f64 100644
--- a/api/src/org/apache/cloudstack/api/command/admin/config/ListCfgsByCmd.java
+++ b/api/src/org/apache/cloudstack/api/command/admin/config/ListCfgsByCmd.java
@@ -19,6 +19,7 @@ package org.apache.cloudstack.api.command.admin.config;
import java.util.ArrayList;
import java.util.List;
+import org.apache.cloudstack.api.response.DomainResponse;
import org.apache.log4j.Logger;
import org.apache.cloudstack.api.APICommand;
@@ -77,6 +78,12 @@ public class ListCfgsByCmd extends BaseListCmd {
description = "the ID of the Account to update the parameter value for corresponding account")
private Long accountId;
+ @Parameter(name = ApiConstants.DOMAIN_ID,
+ type = CommandType.UUID,
+ entityType = DomainResponse.class,
+ description = "the ID of the Domain to update the parameter value for corresponding domain")
+ private Long domainId;
+
@Parameter(name = ApiConstants.IMAGE_STORE_UUID,
type = CommandType.UUID,
entityType = ImageStoreResponse.class,
@@ -111,6 +118,10 @@ public class ListCfgsByCmd extends BaseListCmd {
return accountId;
}
+ public Long getDomainId() {
+ return domainId;
+ }
+
public Long getImageStoreId() {
return imageStoreId;
}
@@ -158,6 +169,9 @@ public class ListCfgsByCmd extends BaseListCmd {
if (getAccountId() != null) {
cfgResponse.setScope("account");
}
+ if (getDomainId() != null) {
+ cfgResponse.setScope("domain");
+ }
if (getImageStoreId() != null){
cfgResponse.setScope("imagestore");
}
diff --git a/api/src/org/apache/cloudstack/api/command/admin/config/UpdateCfgCmd.java b/api/src/org/apache/cloudstack/api/command/admin/config/UpdateCfgCmd.java
index fa5e26e418f..936f0cd69f1 100644
--- a/api/src/org/apache/cloudstack/api/command/admin/config/UpdateCfgCmd.java
+++ b/api/src/org/apache/cloudstack/api/command/admin/config/UpdateCfgCmd.java
@@ -18,6 +18,7 @@ package org.apache.cloudstack.api.command.admin.config;
import com.google.common.base.Strings;
import org.apache.cloudstack.acl.RoleService;
+import org.apache.cloudstack.api.response.DomainResponse;
import org.apache.log4j.Logger;
import org.apache.cloudstack.api.APICommand;
import org.apache.cloudstack.api.ApiArgValidator;
@@ -76,6 +77,12 @@ public class UpdateCfgCmd extends BaseCmd {
description = "the ID of the Account to update the parameter value for corresponding account")
private Long accountId;
+ @Parameter(name = ApiConstants.DOMAIN_ID,
+ type = CommandType.UUID,
+ entityType = DomainResponse.class,
+ description = "the ID of the Domain to update the parameter value for corresponding domain")
+ private Long domainId;
+
@Parameter(name = ApiConstants.IMAGE_STORE_UUID,
type = CommandType.UUID,
entityType = ImageStoreResponse.class,
@@ -115,6 +122,10 @@ public class UpdateCfgCmd extends BaseCmd {
return accountId;
}
+ public Long getDomainId() {
+ return domainId;
+ }
+
public Long getImageStoreId() {
return imageStoreId;
}
@@ -157,6 +168,9 @@ public class UpdateCfgCmd extends BaseCmd {
if (getAccountId() != null) {
response.setScope("account");
}
+ if (getDomainId() != null) {
+ response.setScope("domain");
+ }
response.setValue(value);
this.setResponseObject(response);
} else {
diff --git a/engine/schema/resources/META-INF/cloudstack/core/spring-engine-schema-core-daos-context.xml b/engine/schema/resources/META-INF/cloudstack/core/spring-engine-schema-core-daos-context.xml
index 8a0d7cdde5c..84c27583925 100644
--- a/engine/schema/resources/META-INF/cloudstack/core/spring-engine-schema-core-daos-context.xml
+++ b/engine/schema/resources/META-INF/cloudstack/core/spring-engine-schema-core-daos-context.xml
@@ -147,6 +147,7 @@
+
diff --git a/engine/schema/resources/META-INF/db/schema-41000to41100.sql b/engine/schema/resources/META-INF/db/schema-41000to41100.sql
index 585c7fd4992..283844e96d6 100644
--- a/engine/schema/resources/META-INF/db/schema-41000to41100.sql
+++ b/engine/schema/resources/META-INF/db/schema-41000to41100.sql
@@ -451,7 +451,7 @@ CREATE VIEW `cloud`.`volume_view` AS
`cloud`.`domain` resource_tag_domain ON resource_tag_domain.id = resource_tags.domain_id;
-- Extra Dhcp Options
-CREATE TABLE `cloud`.`nic_extra_dhcp_options` (
+CREATE TABLE IF NOT EXISTS `cloud`.`nic_extra_dhcp_options` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT COMMENT 'id',
`uuid` varchar(255) UNIQUE,
`nic_id` bigint unsigned NOT NULL COMMENT ' nic id where dhcp options are applied',
@@ -523,3 +523,20 @@ ADD COLUMN `forsystemvms` TINYINT(1) NOT NULL DEFAULT '0' COMMENT 'Indicates if
ALTER TABLE `cloud`.`op_dc_ip_address_alloc`
ADD COLUMN `vlan` INT(10) UNSIGNED NULL COMMENT 'Vlan the management network range is on';
+
+-- ldap binding on domain level
+CREATE TABLE IF NOT EXISTS `cloud`.`domain_details` (
+ `id` bigint unsigned NOT NULL auto_increment,
+ `domain_id` bigint unsigned NOT NULL COMMENT 'account id',
+ `name` varchar(255) NOT NULL,
+ `value` varchar(255) NOT NULL,
+ PRIMARY KEY (`id`),
+ CONSTRAINT `fk_domain_details__domain_id` FOREIGN KEY (`domain_id`) REFERENCES `domain`(`id`) ON DELETE CASCADE
+)ENGINE=InnoDB DEFAULT CHARSET=utf8;
+
+ALTER TABLE cloud.ldap_configuration ADD COLUMN domain_id BIGINT(20) DEFAULT NULL;
+ALTER TABLE cloud.ldap_trust_map ADD COLUMN account_id BIGINT(20) DEFAULT 0;
+ALTER TABLE cloud.ldap_trust_map DROP FOREIGN KEY fk_ldap_trust_map__domain_id;
+DROP INDEX uk_ldap_trust_map__domain_id ON cloud.ldap_trust_map;
+CREATE UNIQUE INDEX uk_ldap_trust_map__bind_location ON ldap_trust_map (domain_id, account_id);
+
diff --git a/engine/schema/src/com/cloud/domain/DomainDetailVO.java b/engine/schema/src/com/cloud/domain/DomainDetailVO.java
new file mode 100644
index 00000000000..61eb6cfd28e
--- /dev/null
+++ b/engine/schema/src/com/cloud/domain/DomainDetailVO.java
@@ -0,0 +1,76 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements. See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership. The ASF 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 com.cloud.domain;
+
+import javax.persistence.Column;
+import javax.persistence.Entity;
+import javax.persistence.GeneratedValue;
+import javax.persistence.GenerationType;
+import javax.persistence.Id;
+import javax.persistence.Table;
+
+import com.cloud.utils.db.Encrypt;
+import org.apache.cloudstack.api.InternalIdentity;
+
+@Entity
+@Table(name = "domain_details")
+public class DomainDetailVO implements InternalIdentity {
+ @Id
+ @GeneratedValue(strategy = GenerationType.IDENTITY)
+ @Column(name = "id")
+ private long id;
+
+ @Column(name = "domain_id")
+ private long domainId;
+
+ @Column(name = "name")
+ private String name;
+
+ @Encrypt
+ @Column(name = "value")
+ private String value;
+
+ protected DomainDetailVO() {
+ }
+
+ public DomainDetailVO(long domainId, String name, String value) {
+ this.domainId = domainId;
+ this.name = name;
+ this.value = value;
+ }
+
+ public long getDomainId() {
+ return domainId;
+ }
+
+ public String getName() {
+ return name;
+ }
+
+ public String getValue() {
+ return value;
+ }
+
+ public void setValue(String value) {
+ this.value = value;
+ }
+
+ @Override
+ public long getId() {
+ return id;
+ }
+}
diff --git a/engine/schema/src/com/cloud/domain/dao/DomainDetailsDao.java b/engine/schema/src/com/cloud/domain/dao/DomainDetailsDao.java
new file mode 100644
index 00000000000..51362cf885e
--- /dev/null
+++ b/engine/schema/src/com/cloud/domain/dao/DomainDetailsDao.java
@@ -0,0 +1,34 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements. See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership. The ASF 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 com.cloud.domain.dao;
+
+import java.util.Map;
+
+import com.cloud.domain.DomainDetailVO;
+import com.cloud.utils.db.GenericDao;
+
+public interface DomainDetailsDao extends GenericDao {
+ Map findDetails(long domainId);
+
+ void persist(long domainId, Map details);
+
+ DomainDetailVO findDetail(long domainId, String name);
+
+ void deleteDetails(long domainId);
+
+ void update(long domainId, Map details);
+}
diff --git a/engine/schema/src/com/cloud/domain/dao/DomainDetailsDaoImpl.java b/engine/schema/src/com/cloud/domain/dao/DomainDetailsDaoImpl.java
new file mode 100644
index 00000000000..ad7f7040207
--- /dev/null
+++ b/engine/schema/src/com/cloud/domain/dao/DomainDetailsDaoImpl.java
@@ -0,0 +1,104 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements. See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership. The ASF 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 com.cloud.domain.dao;
+
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import com.cloud.domain.DomainDetailVO;
+import com.cloud.utils.db.GenericDaoBase;
+import com.cloud.utils.db.QueryBuilder;
+import com.cloud.utils.db.SearchBuilder;
+import com.cloud.utils.db.SearchCriteria;
+import com.cloud.utils.db.SearchCriteria.Op;
+import com.cloud.utils.db.TransactionLegacy;
+import org.apache.cloudstack.framework.config.ConfigKey;
+import org.apache.cloudstack.framework.config.ConfigKey.Scope;
+import org.apache.cloudstack.framework.config.ScopedConfigStorage;
+
+public class DomainDetailsDaoImpl extends GenericDaoBase implements DomainDetailsDao, ScopedConfigStorage {
+ protected final SearchBuilder domainSearch;
+
+ protected DomainDetailsDaoImpl() {
+ domainSearch = createSearchBuilder();
+ domainSearch.and("domainId", domainSearch.entity().getDomainId(), Op.EQ);
+ domainSearch.done();
+ }
+
+ @Override
+ public Map findDetails(long domainId) {
+ QueryBuilder sc = QueryBuilder.create(DomainDetailVO.class);
+ sc.and(sc.entity().getDomainId(), Op.EQ, domainId);
+ List results = sc.list();
+ Map details = new HashMap(results.size());
+ for (DomainDetailVO r : results) {
+ details.put(r.getName(), r.getValue());
+ }
+ return details;
+ }
+
+ @Override
+ public void persist(long domainId, Map details) {
+ TransactionLegacy txn = TransactionLegacy.currentTxn();
+ txn.start();
+ SearchCriteria sc = domainSearch.create();
+ sc.setParameters("domainId", domainId);
+ expunge(sc);
+ for (Map.Entry detail : details.entrySet()) {
+ DomainDetailVO vo = new DomainDetailVO(domainId, detail.getKey(), detail.getValue());
+ persist(vo);
+ }
+ txn.commit();
+ }
+
+ @Override
+ public DomainDetailVO findDetail(long domainId, String name) {
+ QueryBuilder sc = QueryBuilder.create(DomainDetailVO.class);
+ sc.and(sc.entity().getDomainId(), Op.EQ, domainId);
+ sc.and(sc.entity().getName(), Op.EQ, name);
+ return sc.find();
+ }
+
+ @Override
+ public void deleteDetails(long domainId) {
+ SearchCriteria sc = domainSearch.create();
+ sc.setParameters("domainId", domainId);
+ List results = search(sc, null);
+ for (DomainDetailVO result : results) {
+ remove(result.getId());
+ }
+ }
+
+ @Override
+ public void update(long domainId, Map details) {
+ Map oldDetails = findDetails(domainId);
+ oldDetails.putAll(details);
+ persist(domainId, oldDetails);
+ }
+
+ @Override
+ public Scope getScope() {
+ return Scope.Domain;
+ }
+
+ @Override
+ public String getConfigValue(long id, ConfigKey> key) {
+ DomainDetailVO vo = findDetail(id, key.key());
+ return vo == null ? null : vo.getValue();
+ }
+}
diff --git a/framework/config/src/org/apache/cloudstack/framework/config/ConfigKey.java b/framework/config/src/org/apache/cloudstack/framework/config/ConfigKey.java
index fb2a57b71f6..1734b98757b 100644
--- a/framework/config/src/org/apache/cloudstack/framework/config/ConfigKey.java
+++ b/framework/config/src/org/apache/cloudstack/framework/config/ConfigKey.java
@@ -31,7 +31,7 @@ import com.cloud.utils.exception.CloudRuntimeException;
public class ConfigKey {
public static enum Scope {
- Global, Zone, Cluster, StoragePool, Account, ManagementServer, ImageStore
+ Global, Zone, Cluster, StoragePool, Account, ManagementServer, ImageStore, Domain
}
private final String _category;
diff --git a/framework/config/src/org/apache/cloudstack/framework/config/impl/ConfigDepotImpl.java b/framework/config/src/org/apache/cloudstack/framework/config/impl/ConfigDepotImpl.java
index e68fd3cdae3..6a85b90b70d 100644
--- a/framework/config/src/org/apache/cloudstack/framework/config/impl/ConfigDepotImpl.java
+++ b/framework/config/src/org/apache/cloudstack/framework/config/impl/ConfigDepotImpl.java
@@ -85,6 +85,7 @@ public class ConfigDepotImpl implements ConfigDepot, ConfigDepotAdmin {
_scopeLevelConfigsMap.put(ConfigKey.Scope.StoragePool, new HashSet>());
_scopeLevelConfigsMap.put(ConfigKey.Scope.Account, new HashSet>());
_scopeLevelConfigsMap.put(ConfigKey.Scope.ImageStore, new HashSet>());
+ _scopeLevelConfigsMap.put(ConfigKey.Scope.Domain, new HashSet>());
}
@Override
diff --git a/plugins/network-elements/juniper-contrail/test/org/apache/cloudstack/network/contrail/management/IntegrationTestConfiguration.java b/plugins/network-elements/juniper-contrail/test/org/apache/cloudstack/network/contrail/management/IntegrationTestConfiguration.java
index 7f1d5b805a8..4105a617e6c 100644
--- a/plugins/network-elements/juniper-contrail/test/org/apache/cloudstack/network/contrail/management/IntegrationTestConfiguration.java
+++ b/plugins/network-elements/juniper-contrail/test/org/apache/cloudstack/network/contrail/management/IntegrationTestConfiguration.java
@@ -140,6 +140,7 @@ import com.cloud.deploy.DeploymentPlanner;
import com.cloud.deploy.DeploymentPlanningManager;
import com.cloud.deploy.dao.PlannerHostReservationDaoImpl;
import com.cloud.domain.dao.DomainDaoImpl;
+import com.cloud.domain.dao.DomainDetailsDaoImpl;
import com.cloud.event.dao.EventDaoImpl;
import com.cloud.event.dao.EventJoinDaoImpl;
import com.cloud.event.dao.UsageEventDaoImpl;
@@ -148,8 +149,8 @@ import com.cloud.host.dao.HostDaoImpl;
import com.cloud.host.dao.HostDetailsDaoImpl;
import com.cloud.host.dao.HostTagsDaoImpl;
import com.cloud.hypervisor.HypervisorGuruManagerImpl;
-import com.cloud.hypervisor.dao.HypervisorCapabilitiesDaoImpl;
import com.cloud.hypervisor.XenServerGuru;
+import com.cloud.hypervisor.dao.HypervisorCapabilitiesDaoImpl;
import com.cloud.network.ExternalDeviceUsageManager;
import com.cloud.network.IpAddress;
import com.cloud.network.IpAddressManagerImpl;
@@ -169,8 +170,8 @@ import com.cloud.network.as.dao.CounterDaoImpl;
import com.cloud.network.dao.AccountGuestVlanMapDaoImpl;
import com.cloud.network.dao.FirewallRulesCidrsDaoImpl;
import com.cloud.network.dao.FirewallRulesDaoImpl;
-import com.cloud.network.dao.IPAddressDaoImpl;
import com.cloud.network.dao.IPAddressDao;
+import com.cloud.network.dao.IPAddressDaoImpl;
import com.cloud.network.dao.LBHealthCheckPolicyDaoImpl;
import com.cloud.network.dao.LBStickinessPolicyDaoImpl;
import com.cloud.network.dao.LoadBalancerDaoImpl;
@@ -308,7 +309,7 @@ import com.cloud.vm.snapshot.dao.VMSnapshotDaoImpl;
ConditionDaoImpl.class, ConfigurationDaoImpl.class, ConfigurationManagerImpl.class, ConfigurationServerImpl.class, ConsoleProxyDaoImpl.class,
ContrailElementImpl.class, ContrailGuru.class, ContrailManagerImpl.class, CounterDaoImpl.class, DataCenterDaoImpl.class, DataCenterDetailsDaoImpl.class, DataCenterIpAddressDaoImpl.class,
DataCenterJoinDaoImpl.class, DataCenterLinkLocalIpAddressDaoImpl.class, DataCenterVnetDaoImpl.class, DcDetailsDaoImpl.class, DedicatedResourceDaoImpl.class,
- DiskOfferingDaoImpl.class, DiskOfferingJoinDaoImpl.class, DomainDaoImpl.class, DomainManagerImpl.class, DomainRouterDaoImpl.class, DomainRouterJoinDaoImpl.class,
+ DiskOfferingDaoImpl.class, DiskOfferingJoinDaoImpl.class, DomainDaoImpl.class, DomainDetailsDaoImpl.class, DomainManagerImpl.class, DomainRouterDaoImpl.class, DomainRouterJoinDaoImpl.class,
EventDaoImpl.class, EventJoinDaoImpl.class, EventUtils.class, ExtensionRegistry.class, FirewallManagerImpl.class, FirewallRulesCidrsDaoImpl.class,
FirewallRulesDaoImpl.class, GuestOSCategoryDaoImpl.class, GuestOSDaoImpl.class, HostDaoImpl.class, HostDetailsDaoImpl.class, HostJoinDaoImpl.class,
HostPodDaoImpl.class, HostTagsDaoImpl.class, HostTransferMapDaoImpl.class, HypervisorCapabilitiesDaoImpl.class, HypervisorGuruManagerImpl.class,
diff --git a/plugins/network-elements/juniper-contrail/test/org/apache/cloudstack/network/contrail/management/MockAccountManager.java b/plugins/network-elements/juniper-contrail/test/org/apache/cloudstack/network/contrail/management/MockAccountManager.java
index fa933244a66..37ca2bccff4 100644
--- a/plugins/network-elements/juniper-contrail/test/org/apache/cloudstack/network/contrail/management/MockAccountManager.java
+++ b/plugins/network-elements/juniper-contrail/test/org/apache/cloudstack/network/contrail/management/MockAccountManager.java
@@ -317,7 +317,13 @@ public class MockAccountManager extends ManagerBase implements AccountManager {
return false;
}
- @Override public boolean moveUser(MoveUserCmd moveUserCmd) {
+ @Override
+ public boolean moveUser(MoveUserCmd moveUserCmd) {
+ return false;
+ }
+
+ @Override
+ public boolean moveUser(long id, Long domainId, long accountId) {
return false;
}
diff --git a/plugins/user-authenticators/ldap/pom.xml b/plugins/user-authenticators/ldap/pom.xml
index 9f97f08f3fd..e2b0ead17e0 100644
--- a/plugins/user-authenticators/ldap/pom.xml
+++ b/plugins/user-authenticators/ldap/pom.xml
@@ -37,9 +37,9 @@
- test/groovy
+ test
- **/*.groovy
+ groovy/**/*.groovy
@@ -70,7 +70,8 @@
maven-surefire-plugin
- **/*Spec*
+ **/*Spec.groovy
+ **/*Test.java
@@ -90,6 +91,7 @@
+ test
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LDAPConfigCmd.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LDAPConfigCmd.java
index a138e7ddd4a..cfef21e2aff 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LDAPConfigCmd.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LDAPConfigCmd.java
@@ -49,7 +49,7 @@ import com.cloud.utils.Pair;
* @deprecated as of 4.3 use the new api {@link LdapAddConfigurationCmd}
*/
@Deprecated
-@APICommand(name = "ldapConfig", description = "Configure the LDAP context for this site.", responseObject = LDAPConfigResponse.class, since = "3.0.0",
+@APICommand(name = "ldapConfig", description = "(Deprecated, use addLdapConfiguration) Configure the LDAP context for this site.", responseObject = LDAPConfigResponse.class, since = "3.0.0",
requestHasSensitiveInfo = true, responseHasSensitiveInfo = false)
public class LDAPConfigCmd extends BaseCmd {
@@ -190,8 +190,8 @@ public class LDAPConfigCmd extends BaseCmd {
if (result.second() > 0) {
boolean useSSlConfig = _ldapConfiguration.getSSLStatus();
- String searchBaseConfig = _ldapConfiguration.getBaseDn();
- String bindDnConfig = _ldapConfiguration.getBindPrincipal();
+ String searchBaseConfig = _ldapConfiguration.getBaseDn(null);
+ String bindDnConfig = _ldapConfiguration.getBindPrincipal(null);
for (LdapConfigurationVO ldapConfigurationVO : result.first()) {
responses.add(createLDAPConfigResponse(ldapConfigurationVO.getHostname(), ldapConfigurationVO.getPort(), useSSlConfig, null, searchBaseConfig,
bindDnConfig));
@@ -226,7 +226,7 @@ public class LDAPConfigCmd extends BaseCmd {
}
private boolean updateLDAP() {
- _ldapManager.addConfiguration(hostname, port);
+ _ldapManager.addConfiguration(hostname, port, null);
/**
* There is no query filter now. It is derived from ldap.user.object and ldap.search.group.principle
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LDAPRemoveCmd.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LDAPRemoveCmd.java
index eb3729d9d9e..0a4dc20ee0b 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LDAPRemoveCmd.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LDAPRemoveCmd.java
@@ -35,7 +35,7 @@ import com.cloud.utils.Pair;
* @deprecated as of 4.3 use the new api {@link LdapDeleteConfigurationCmd}
*/
@Deprecated
-@APICommand(name = "ldapRemove", description = "Remove the LDAP context for this site.", responseObject = LDAPConfigResponse.class, since = "3.0.1",
+@APICommand(name = "ldapRemove", description = "(Deprecated , use deleteLdapConfiguration) Remove the LDAP context for this site.", responseObject = LDAPConfigResponse.class, since = "3.0.1",
requestHasSensitiveInfo = false, responseHasSensitiveInfo = false)
public class LDAPRemoveCmd extends BaseCmd {
public static final Logger s_logger = Logger.getLogger(LDAPRemoveCmd.class.getName());
@@ -60,7 +60,7 @@ public class LDAPRemoveCmd extends BaseCmd {
LdapListConfigurationCmd listConfigurationCmd = new LdapListConfigurationCmd(_ldapManager);
Pair, Integer> result = _ldapManager.listConfigurations(listConfigurationCmd);
for (LdapConfigurationVO config : result.first()) {
- _ldapManager.deleteConfiguration(config.getHostname());
+ _ldapManager.deleteConfiguration(config.getHostname(), 0, null);
}
return true;
}
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapAddConfigurationCmd.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapAddConfigurationCmd.java
index 555d1a987fd..7c592888364 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapAddConfigurationCmd.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapAddConfigurationCmd.java
@@ -18,6 +18,8 @@ package org.apache.cloudstack.api.command;
import javax.inject.Inject;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.response.DomainResponse;
import org.apache.log4j.Logger;
import org.apache.cloudstack.api.APICommand;
@@ -40,12 +42,15 @@ public class LdapAddConfigurationCmd extends BaseCmd {
@Inject
private LdapManager _ldapManager;
- @Parameter(name = "hostname", type = CommandType.STRING, required = true, description = "Hostname")
+ @Parameter(name = ApiConstants.HOST_NAME, type = CommandType.STRING, required = true, description = "Hostname")
private String hostname;
- @Parameter(name = "port", type = CommandType.INTEGER, required = true, description = "Port")
+ @Parameter(name = ApiConstants.PORT, type = CommandType.INTEGER, required = true, description = "Port")
private int port;
+ @Parameter(name = ApiConstants.DOMAIN_ID, type = CommandType.UUID, required = false, entityType = DomainResponse.class, description = "linked domain")
+ private Long domainId;
+
public LdapAddConfigurationCmd() {
super();
}
@@ -58,7 +63,7 @@ public class LdapAddConfigurationCmd extends BaseCmd {
@Override
public void execute() throws ServerApiException {
try {
- final LdapConfigurationResponse response = _ldapManager.addConfiguration(hostname, port);
+ final LdapConfigurationResponse response = _ldapManager.addConfiguration(hostname, port, domainId);
response.setObjectName("LdapAddConfiguration");
response.setResponseName(getCommandName());
setResponseObject(response);
@@ -86,6 +91,10 @@ public class LdapAddConfigurationCmd extends BaseCmd {
return port;
}
+ public Long getDomainId() {
+ return domainId;
+ }
+
public void setHostname(final String hostname) {
this.hostname = hostname;
}
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapCreateAccountCmd.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapCreateAccountCmd.java
index d845857925d..6e69259ebdd 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapCreateAccountCmd.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapCreateAccountCmd.java
@@ -139,7 +139,7 @@ public class LdapCreateAccountCmd extends BaseCmd {
Long finalDomainId = getDomainId();
callContext.setEventDetails("Account Name: " + finalAccountName + ", Domain Id:" + finalDomainId);
try {
- final LdapUser user = _ldapManager.getUser(username);
+ final LdapUser user = _ldapManager.getUser(username, domainId);
validateUser(user);
final UserAccount userAccount = createCloudstackUserAccount(user, finalAccountName, finalDomainId);
if (userAccount != null) {
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapDeleteConfigurationCmd.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapDeleteConfigurationCmd.java
index 30b37d8b88d..3ffebecfb95 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapDeleteConfigurationCmd.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapDeleteConfigurationCmd.java
@@ -18,6 +18,8 @@ package org.apache.cloudstack.api.command;
import javax.inject.Inject;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.response.DomainResponse;
import org.apache.log4j.Logger;
import org.apache.cloudstack.api.APICommand;
@@ -40,9 +42,16 @@ public class LdapDeleteConfigurationCmd extends BaseCmd {
@Inject
private LdapManager _ldapManager;
- @Parameter(name = "hostname", type = CommandType.STRING, required = true, description = "Hostname")
+
+ @Parameter(name = ApiConstants.HOST_NAME, type = CommandType.STRING, required = true, description = "Hostname")
private String hostname;
+ @Parameter(name = ApiConstants.PORT, type = CommandType.INTEGER, required = false, description = "port")
+ private int port;
+
+ @Parameter(name = ApiConstants.DOMAIN_ID, type = CommandType.UUID, required = false, entityType = DomainResponse.class, description = "linked domain")
+ private Long domainId;
+
public LdapDeleteConfigurationCmd() {
super();
}
@@ -52,10 +61,22 @@ public class LdapDeleteConfigurationCmd extends BaseCmd {
_ldapManager = ldapManager;
}
+ public String getHostname() {
+ return hostname;
+ }
+
+ public int getPort() {
+ return port;
+ }
+
+ public Long getDomainId() {
+ return domainId;
+ }
+
@Override
public void execute() throws ServerApiException {
try {
- final LdapConfigurationResponse response = _ldapManager.deleteConfiguration(hostname);
+ final LdapConfigurationResponse response = _ldapManager.deleteConfiguration(this);
response.setObjectName("LdapDeleteConfiguration");
response.setResponseName(getCommandName());
setResponseObject(response);
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapImportUsersCmd.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapImportUsersCmd.java
index 9fdd700638c..564c1d0a1ef 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapImportUsersCmd.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapImportUsersCmd.java
@@ -142,9 +142,9 @@ public class LdapImportUsersCmd extends BaseListCmd {
try {
if (StringUtils.isNotBlank(groupName)) {
- users = _ldapManager.getUsersInGroup(groupName);
+ users = _ldapManager.getUsersInGroup(groupName, domainId);
} else {
- users = _ldapManager.getUsers();
+ users = _ldapManager.getUsers(domainId);
}
} catch (NoLdapUserMatchingQueryException ex) {
users = new ArrayList();
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapListConfigurationCmd.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapListConfigurationCmd.java
index 050fb36cb19..db6318e6b2c 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapListConfigurationCmd.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapListConfigurationCmd.java
@@ -21,6 +21,8 @@ import java.util.List;
import javax.inject.Inject;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.response.DomainResponse;
import org.apache.log4j.Logger;
import org.apache.cloudstack.api.APICommand;
@@ -44,12 +46,15 @@ public class LdapListConfigurationCmd extends BaseListCmd {
@Inject
private LdapManager _ldapManager;
- @Parameter(name = "hostname", type = CommandType.STRING, required = false, description = "Hostname")
+ @Parameter(name = ApiConstants. HOST_NAME, type = CommandType.STRING, required = false, description = "Hostname")
private String hostname;
- @Parameter(name = "port", type = CommandType.INTEGER, required = false, description = "Port")
+ @Parameter(name = ApiConstants.PORT, type = CommandType.INTEGER, required = false, description = "Port")
private int port;
+ @Parameter(name = ApiConstants.DOMAIN_ID, type = CommandType.UUID, required = false, entityType = DomainResponse.class, description = "linked domain")
+ private Long domainId;
+
public LdapListConfigurationCmd() {
super();
}
@@ -97,6 +102,10 @@ public class LdapListConfigurationCmd extends BaseListCmd {
return port;
}
+ public Long getDomainId() {
+ return domainId;
+ }
+
public void setHostname(final String hostname) {
this.hostname = hostname;
}
@@ -104,4 +113,8 @@ public class LdapListConfigurationCmd extends BaseListCmd {
public void setPort(final int port) {
this.port = port;
}
+
+ public void setDomainId(final Long domainId) {
+ this.domainId = domainId;
+ }
}
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapListUsersCmd.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapListUsersCmd.java
index e655f5f4ac0..b2266dc8fd3 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapListUsersCmd.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LdapListUsersCmd.java
@@ -83,7 +83,7 @@ public class LdapListUsersCmd extends BaseListCmd {
List ldapResponses = null;
final ListResponse response = new ListResponse();
try {
- final List users = _ldapManager.getUsers();
+ final List users = _ldapManager.getUsers(null);
ldapResponses = createLdapUserResponse(users);
} catch (final NoLdapUserMatchingQueryException ex) {
ldapResponses = new ArrayList();
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LinkAccountToLdapCmd.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LinkAccountToLdapCmd.java
new file mode 100644
index 00000000000..52adc664ff8
--- /dev/null
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LinkAccountToLdapCmd.java
@@ -0,0 +1,142 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF 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.apache.cloudstack.api.command;
+
+import com.cloud.exception.InvalidParameterValueException;
+import com.cloud.user.Account;
+import com.cloud.user.User;
+import com.cloud.user.UserAccount;
+import org.apache.cloudstack.acl.RoleType;
+import org.apache.cloudstack.api.APICommand;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.ApiErrorCode;
+import org.apache.cloudstack.api.BaseCmd;
+import org.apache.cloudstack.api.Parameter;
+import org.apache.cloudstack.api.ServerApiException;
+import org.apache.cloudstack.api.response.DomainResponse;
+import org.apache.cloudstack.api.response.LinkAccountToLdapResponse;
+import org.apache.cloudstack.api.response.LinkDomainToLdapResponse;
+import org.apache.cloudstack.ldap.LdapManager;
+import org.apache.cloudstack.ldap.LdapUser;
+import org.apache.cloudstack.ldap.NoLdapUserMatchingQueryException;
+import org.apache.log4j.Logger;
+
+import javax.inject.Inject;
+import java.util.UUID;
+
+@APICommand(name = LinkAccountToLdapCmd.APINAME, description = "link a cloudstack account to a group or OU in ldap", responseObject = LinkDomainToLdapResponse.class, since = "4.11.0",
+ requestHasSensitiveInfo = false, responseHasSensitiveInfo = false, authorized = {RoleType.Admin,RoleType.DomainAdmin})
+public class LinkAccountToLdapCmd extends BaseCmd {
+ public static final Logger LOGGER = Logger.getLogger(LinkAccountToLdapCmd.class.getName());
+ public static final String APINAME = "linkAccountToLdap";
+
+ @Parameter(name = ApiConstants.DOMAIN_ID, type = CommandType.UUID, required = true, entityType = DomainResponse.class, description = "The id of the domain that is to contain the linked account.")
+ private Long domainId;
+
+ @Parameter(name = ApiConstants.TYPE, type = CommandType.STRING, required = false, description = "type of the ldap name. GROUP or OU, defaults to GROUP")
+ private String type;
+
+ @Parameter(name = ApiConstants.LDAP_DOMAIN, type = CommandType.STRING, required = true, description = "name of the group or OU in LDAP")
+ private String ldapDomain;
+
+ @Parameter(name = ApiConstants.ACCOUNT, type = CommandType.STRING, required = true, description = "name of the account, it will be created if it does not exist")
+ private String accountName;
+
+ @Parameter(name = ApiConstants.ADMIN, type = CommandType.STRING, required = false, description = "domain admin username in LDAP ")
+ private String admin;
+
+ @Parameter(name = ApiConstants.ACCOUNT_TYPE, type = CommandType.SHORT, required = true, description = "Type of the account to auto import. Specify 0 for user and 2 for "
+ + "domain admin")
+ private short accountType;
+
+ @Inject
+ private LdapManager _ldapManager;
+
+ @Override
+ public void execute() throws ServerApiException {
+ try {
+ LinkAccountToLdapResponse response = _ldapManager.linkAccountToLdap(this);
+ if (admin != null) {
+ LdapUser ldapUser = null;
+ try {
+ ldapUser = _ldapManager.getUser(admin, type, ldapDomain, domainId);
+ } catch (NoLdapUserMatchingQueryException e) {
+ LOGGER.debug("no ldap user matching username " + admin + " in the given group/ou", e);
+ }
+ if (ldapUser != null && !ldapUser.isDisabled()) {
+ Account account = _accountService.getActiveAccountByName(admin, domainId);
+ if (account == null) {
+ try {
+ UserAccount userAccount = _accountService
+ .createUserAccount(admin, "", ldapUser.getFirstname(), ldapUser.getLastname(), ldapUser.getEmail(), null, admin, Account.ACCOUNT_TYPE_DOMAIN_ADMIN, RoleType.DomainAdmin.getId(), domainId, null, null, UUID.randomUUID().toString(),
+ UUID.randomUUID().toString(), User.Source.LDAP);
+ response.setAdminId(String.valueOf(userAccount.getAccountId()));
+ LOGGER.info("created an account with name " + admin + " in the given domain " + domainId);
+ } catch (Exception e) {
+ LOGGER.info("an exception occurred while creating account with name " + admin + " in domain " + domainId, e);
+ }
+ } else {
+ LOGGER.debug("an account with name " + admin + " already exists in the domain " + domainId);
+ }
+ } else {
+ LOGGER.debug("ldap user with username " + admin + " is disabled in the given group/ou");
+ }
+ }
+ response.setObjectName(APINAME);
+ response.setResponseName(getCommandName());
+ setResponseObject(response);
+ } catch (final InvalidParameterValueException e) {
+ throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, e.toString());
+ }
+ }
+
+ @Override
+ public String getCommandName() {
+ return APINAME.toLowerCase() + BaseCmd.RESPONSE_SUFFIX;
+ }
+
+ @Override
+ public long getEntityOwnerId() {
+ return Account.ACCOUNT_ID_SYSTEM;
+ }
+
+ public Long getDomainId() {
+ return domainId;
+ }
+
+ public String getType() {
+ return type;
+ }
+
+ public String getLdapDomain() {
+ return ldapDomain;
+ }
+
+ public String getAccountName() {
+ return accountName;
+ }
+
+ public String getAdmin() {
+ return admin;
+ }
+
+ public short getAccountType() {
+ return accountType;
+ }
+}
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LinkDomainToLdapCmd.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LinkDomainToLdapCmd.java
index 477e80f2556..00140952051 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LinkDomainToLdapCmd.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/command/LinkDomainToLdapCmd.java
@@ -54,6 +54,10 @@ public class LinkDomainToLdapCmd extends BaseCmd {
@Parameter(name = ApiConstants.TYPE, type = CommandType.STRING, required = true, description = "type of the ldap name. GROUP or OU")
private String type;
+ @Parameter(name = ApiConstants.LDAP_DOMAIN, type = CommandType.STRING, required = true, description = "name of the group or OU in LDAP")
+ private String ldapDomain;
+
+ @Deprecated
@Parameter(name = ApiConstants.NAME, type = CommandType.STRING, required = true, description = "name of the group or OU in LDAP")
private String name;
@@ -67,14 +71,35 @@ public class LinkDomainToLdapCmd extends BaseCmd {
@Inject
private LdapManager _ldapManager;
+ public Long getDomainId() {
+ return domainId;
+ }
+
+ public String getType() {
+ return type;
+ }
+
+ public String getLdapDomain() {
+ return ldapDomain == null ? name : ldapDomain;
+ }
+
+ public String getAdmin() {
+ return admin;
+ }
+
+ public short getAccountType() {
+ return accountType;
+ }
+
+
@Override
public void execute() throws ServerApiException {
try {
- LinkDomainToLdapResponse response = _ldapManager.linkDomainToLdap(domainId, type, name, accountType);
+ LinkDomainToLdapResponse response = _ldapManager.linkDomainToLdap(this);
if(admin!=null) {
LdapUser ldapUser = null;
try {
- ldapUser = _ldapManager.getUser(admin, type, name);
+ ldapUser = _ldapManager.getUser(admin, type, getLdapDomain(), domainId);
} catch (NoLdapUserMatchingQueryException e) {
s_logger.debug("no ldap user matching username " + admin + " in the given group/ou", e);
}
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/response/LdapConfigurationResponse.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/response/LdapConfigurationResponse.java
index a4e47828844..c6d2bf38cb2 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/response/LdapConfigurationResponse.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/response/LdapConfigurationResponse.java
@@ -18,31 +18,44 @@ package org.apache.cloudstack.api.response;
import com.google.gson.annotations.SerializedName;
+import org.apache.cloudstack.api.ApiConstants;
import org.apache.cloudstack.api.BaseResponse;
import com.cloud.serializer.Param;
+import org.apache.cloudstack.api.EntityReference;
+import org.apache.cloudstack.ldap.LdapConfiguration;
+@EntityReference(value = LdapConfiguration.class)
public class LdapConfigurationResponse extends BaseResponse {
- @SerializedName("hostname")
- @Param(description = "hostname")
+ @SerializedName(ApiConstants.HOST_NAME)
+ @Param(description = "name of the host running the ldap server")
private String hostname;
- @SerializedName("port")
- @Param(description = "port")
+ @SerializedName(ApiConstants.PORT)
+ @Param(description = "port teh ldap server is running on")
private int port;
+ @SerializedName(ApiConstants.DOMAIN_ID)
+ @Param(description = "linked domain")
+ private String domainId;
+
public LdapConfigurationResponse() {
super();
}
public LdapConfigurationResponse(final String hostname) {
super();
- this.hostname = hostname;
+ setHostname(hostname);
}
public LdapConfigurationResponse(final String hostname, final int port) {
- this.hostname = hostname;
- this.port = port;
+ this(hostname);
+ setPort(port);
+ }
+
+ public LdapConfigurationResponse(final String hostname, final int port, final String domainId) {
+ this(hostname, port);
+ setDomainId(domainId);
}
public String getHostname() {
@@ -60,4 +73,12 @@ public class LdapConfigurationResponse extends BaseResponse {
public void setPort(final int port) {
this.port = port;
}
+
+ public String getDomainId() {
+ return domainId;
+ }
+
+ public void setDomainId(String domainId) {
+ this.domainId = domainId;
+ }
}
\ No newline at end of file
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/response/LinkAccountToLdapResponse.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/response/LinkAccountToLdapResponse.java
new file mode 100644
index 00000000000..23456e71641
--- /dev/null
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/response/LinkAccountToLdapResponse.java
@@ -0,0 +1,85 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF 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.apache.cloudstack.api.response;
+
+import com.cloud.serializer.Param;
+import com.google.gson.annotations.SerializedName;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.BaseResponse;
+
+public class LinkAccountToLdapResponse extends BaseResponse {
+
+ @SerializedName(ApiConstants.DOMAIN_ID)
+ @Param(description = "id of the Domain which is linked to LDAP")
+ private String domainId;
+
+ @SerializedName(ApiConstants.LDAP_DOMAIN)
+ @Param(description = "name of the group or OU in LDAP which is linked to the domain")
+ private String ldapDomain;
+
+ @SerializedName(ApiConstants.TYPE)
+ @Param(description = "type of the name in LDAP which is linke to the domain")
+ private String type;
+
+ @SerializedName(ApiConstants.ACCOUNT_TYPE)
+ @Param(description = "Type of the account to auto import")
+ private short accountType;
+
+ @SerializedName(ApiConstants.ACCOUNT_ID)
+ @Param(description = "Domain Admin accountId that is created")
+ private String adminId;
+
+ @SerializedName(ApiConstants.ACCOUNT)
+ @Param(description = "name of the account")
+ private String accountName;
+
+
+ public LinkAccountToLdapResponse(String domainId, String type, String ldapDomain, short accountType, String adminId, String accountName) {
+ this.domainId = domainId;
+ this.type = type;
+ this.ldapDomain = ldapDomain;
+ this.accountType = accountType;
+ this.adminId = adminId;
+ this.accountName = accountName;
+ }
+
+ public String getDomainId() {
+ return domainId;
+ }
+
+ public String getLdapDomain() {
+ return ldapDomain;
+ }
+
+ public String getType() {
+ return type;
+ }
+
+ public short getAccountType() {
+ return accountType;
+ }
+
+ public String getAdminId() {
+ return adminId;
+ }
+
+ public void setAdminId(String adminId) {
+ this.adminId = adminId;
+ }
+}
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/response/LinkDomainToLdapResponse.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/response/LinkDomainToLdapResponse.java
index 050eb6c3eb5..d6d4b55e257 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/response/LinkDomainToLdapResponse.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/api/response/LinkDomainToLdapResponse.java
@@ -66,11 +66,6 @@ public class LinkDomainToLdapResponse extends BaseResponse {
return ldapDomain == null ? name : ldapDomain;
}
- @Deprecated
- public String getName() {
- return ldapDomain == null ? name : ldapDomain;
- }
-
public String getType() {
return type;
}
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/ADLdapUserManagerImpl.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/ADLdapUserManagerImpl.java
index 0df638ad228..e844df57c1c 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/ADLdapUserManagerImpl.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/ADLdapUserManagerImpl.java
@@ -36,38 +36,38 @@ public class ADLdapUserManagerImpl extends OpenLdapUserManagerImpl implements Ld
private static final String MICROSOFT_AD_MEMBERS_FILTER = "memberOf";
@Override
- public List getUsersInGroup(String groupName, LdapContext context) throws NamingException {
+ public List getUsersInGroup(String groupName, LdapContext context, Long domainId) throws NamingException {
if (StringUtils.isBlank(groupName)) {
throw new IllegalArgumentException("ldap group name cannot be blank");
}
- String basedn = _ldapConfiguration.getBaseDn();
+ String basedn = _ldapConfiguration.getBaseDn(domainId);
if (StringUtils.isBlank(basedn)) {
throw new IllegalArgumentException("ldap basedn is not configured");
}
final SearchControls searchControls = new SearchControls();
searchControls.setSearchScope(_ldapConfiguration.getScope());
- searchControls.setReturningAttributes(_ldapConfiguration.getReturnAttributes());
+ searchControls.setReturningAttributes(_ldapConfiguration.getReturnAttributes(domainId));
- NamingEnumeration results = context.search(basedn, generateADGroupSearchFilter(groupName), searchControls);
+ NamingEnumeration results = context.search(basedn, generateADGroupSearchFilter(groupName, domainId), searchControls);
final List users = new ArrayList();
while (results.hasMoreElements()) {
final SearchResult result = results.nextElement();
- users.add(createUser(result));
+ users.add(createUser(result, domainId));
}
return users;
}
- private String generateADGroupSearchFilter(String groupName) {
+ private String generateADGroupSearchFilter(String groupName, Long domainId) {
final StringBuilder userObjectFilter = new StringBuilder();
userObjectFilter.append("(objectClass=");
- userObjectFilter.append(_ldapConfiguration.getUserObject());
+ userObjectFilter.append(_ldapConfiguration.getUserObject(domainId));
userObjectFilter.append(")");
final StringBuilder memberOfFilter = new StringBuilder();
- String groupCnName = _ldapConfiguration.getCommonNameAttribute() + "=" +groupName + "," + _ldapConfiguration.getBaseDn();
- memberOfFilter.append("(").append(getMemberOfAttribute()).append("=");
+ String groupCnName = _ldapConfiguration.getCommonNameAttribute() + "=" +groupName + "," + _ldapConfiguration.getBaseDn(domainId);
+ memberOfFilter.append("(").append(getMemberOfAttribute(domainId)).append("=");
memberOfFilter.append(groupCnName);
memberOfFilter.append(")");
@@ -94,8 +94,8 @@ public class ADLdapUserManagerImpl extends OpenLdapUserManagerImpl implements Ld
return isDisabledUser;
}
- protected String getMemberOfAttribute() {
- if(_ldapConfiguration.isNestedGroupsEnabled()) {
+ protected String getMemberOfAttribute(final Long domainId) {
+ if(_ldapConfiguration.isNestedGroupsEnabled(domainId)) {
return MICROSOFT_AD_NESTED_MEMBERS_FILTER;
} else {
return MICROSOFT_AD_MEMBERS_FILTER;
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapAuthenticator.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapAuthenticator.java
index add39c5b13d..cd4ed3d5cea 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapAuthenticator.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapAuthenticator.java
@@ -16,6 +16,8 @@
// under the License.
package org.apache.cloudstack.ldap;
+import java.util.ArrayList;
+import java.util.List;
import java.util.Map;
import java.util.UUID;
@@ -56,60 +58,181 @@ public class LdapAuthenticator extends AdapterBase implements UserAuthenticator
@Override
public Pair authenticate(final String username, final String password, final Long domainId, final Map requestParameters) {
+ Pair rc = new Pair(false, null);
+ // TODO not allowing an empty password is a policy we shouldn't decide on. A private cloud may well want to allow this.
if (StringUtils.isEmpty(username) || StringUtils.isEmpty(password)) {
s_logger.debug("Username or Password cannot be empty");
- return new Pair(false, null);
+ return rc;
}
- boolean result = false;
- ActionOnFailedAuthentication action = null;
-
if (_ldapManager.isLdapEnabled()) {
final UserAccount user = _userAccountDao.getUserAccount(username, domainId);
- LdapTrustMapVO ldapTrustMapVO = _ldapManager.getDomainLinkedToLdap(domainId);
- if(ldapTrustMapVO != null) {
- try {
- LdapUser ldapUser = _ldapManager.getUser(username, ldapTrustMapVO.getType().toString(), ldapTrustMapVO.getName());
- if(!ldapUser.isDisabled()) {
- result = _ldapManager.canAuthenticate(ldapUser.getPrincipal(), password);
- if(result) {
- if(user == null) {
- // import user to cloudstack
- createCloudStackUserAccount(ldapUser, domainId, ldapTrustMapVO.getAccountType());
- } else {
- enableUserInCloudStack(user);
- }
- }
- } else {
- //disable user in cloudstack
- disableUserInCloudStack(user);
- }
- } catch (NoLdapUserMatchingQueryException e) {
- s_logger.debug(e.getMessage());
+ List ldapTrustMapVOs = _ldapManager.getDomainLinkage(domainId);
+ if(ldapTrustMapVOs != null && ldapTrustMapVOs.size() > 0) {
+ if(ldapTrustMapVOs.size() == 1 && ldapTrustMapVOs.get(0).getAccountId() == 0) {
+ // We have a single mapping of a domain to an ldap group or ou
+ return authenticate(username, password, domainId, user, ldapTrustMapVOs.get(0));
+ } else {
+ // we are dealing with mapping of accounts in a domain to ldap groups
+ return authenticate(username, password, domainId, user, ldapTrustMapVOs);
}
-
} else {
//domain is not linked to ldap follow normal authentication
- if(user != null ) {
- try {
- LdapUser ldapUser = _ldapManager.getUser(username);
- if(!ldapUser.isDisabled()) {
- result = _ldapManager.canAuthenticate(ldapUser.getPrincipal(), password);
- } else {
- s_logger.debug("user with principal "+ ldapUser.getPrincipal() + " is disabled in ldap");
- }
- } catch (NoLdapUserMatchingQueryException e) {
- s_logger.debug(e.getMessage());
- }
- }
- }
- if (!result && user != null) {
- action = ActionOnFailedAuthentication.INCREMENT_INCORRECT_LOGIN_ATTEMPT_COUNT;
+ return authenticate(username, password, domainId, user);
}
}
- return new Pair(result, action);
+ return rc;
+ }
+
+ /**
+ * checks if the user exists in ldap and create in cloudstack if needed.
+ *
+ * @param username login id
+ * @param password pass phrase
+ * @param domainId domain the user is trying to log on to
+ * @param userAccount cloudstack user object
+ * @param ldapTrustMapVOs the trust mappings of accounts in the domain to ldap groups
+ * @return false if the ldap user object does not exist, is not mapped to an account, is mapped to multiple accounts or if authenitication fails
+ */
+ private Pair authenticate(String username, String password, Long domainId, UserAccount userAccount, List ldapTrustMapVOs) {
+ Pair rc = new Pair(false, null);
+ try {
+ LdapUser ldapUser = _ldapManager.getUser(username, domainId);
+ List memberships = ldapUser.getMemberships();
+ List mappedGroups = getMappedGroups(ldapTrustMapVOs);
+ mappedGroups.retainAll(memberships);
+ // check membership, there must be only one match in this domain
+ if(ldapUser.isDisabled()) {
+ logAndDisable(userAccount, "attempt to log on using disabled ldap user " + userAccount.getUsername(), false);
+ } else if(mappedGroups.size() > 1) {
+ logAndDisable(userAccount, "user '" + username + "' is mapped to more then one account in domain and will be disabled.", false);
+ } else if(mappedGroups.size() < 1) {
+ logAndDisable(userAccount, "user '" + username + "' is not mapped to an account in domain and will be removed.", true);
+ } else {
+ // a valid ldap configured user exists
+ LdapTrustMapVO mapping = _ldapManager.getLinkedLdapGroup(domainId,mappedGroups.get(0));
+ // we could now assert that ldapTrustMapVOs.contains(mapping);
+ // createUser in Account can only be done by account name not by account id
+ String accountName = _accountManager.getAccount(mapping.getAccountId()).getAccountName();
+ rc.first(_ldapManager.canAuthenticate(ldapUser.getPrincipal(), password, domainId));
+ // for security reasons we keep processing on faulty login attempt to not give a way information on userid existence
+ if (userAccount == null) {
+ // new user that is in ldap; authenticate and create
+ User user = _accountManager.createUser(username, "", ldapUser.getFirstname(), ldapUser.getLastname(), ldapUser.getEmail(), null, accountName,
+ domainId, UUID.randomUUID().toString(), User.Source.LDAP);
+ /* expected error conditions:
+ *
+ * caught in APIServlet: CloudRuntimeException("The domain " + domainId + " does not exist; unable to create user");
+ * caught in APIServlet: CloudRuntimeException("The user cannot be created as domain " + domain.getName() + " is being deleted");
+ * would have been thrown above: InvalidParameterValueException("Unable to find account " + accountName + " in domain id=" + domainId + " to create user");
+ * we are system user: PermissionDeniedException("Account id : " + account.getId() + " is a system account, can't add a user to it");
+ * serious and must be thrown: CloudRuntimeException("The user " + userName + " already exists in domain " + domainId);
+ * fatal system error and must be thrown: CloudRuntimeException("Failed to encode password");
+ */
+ userAccount = _accountManager.getUserAccountById(user.getId());
+ } else {
+ // not a new user, check if mapped group has changed
+ if(userAccount.getAccountId() != mapping.getAccountId()) {
+ _accountManager.moveUser(userAccount.getId(),userAccount.getDomainId(),mapping.getAccountId());
+ }
+ // else { the user hasn't changed in ldap, the ldap group stayed the same, hurray, pass, fun thou self a lot of fun }
+ }
+ }
+ } catch (NoLdapUserMatchingQueryException e) {
+ s_logger.debug(e.getMessage());
+ disableUserInCloudStack(userAccount);
+ }
+
+ return rc;
+ }
+
+ private void logAndDisable(UserAccount userAccount, String msg, boolean remove) {
+ if (s_logger.isInfoEnabled()) {
+ s_logger.info(msg);
+ }
+ if(remove) {
+ removeUserInCloudStack(userAccount);
+ } else {
+ disableUserInCloudStack(userAccount);
+ }
+ }
+
+ private List getMappedGroups(List ldapTrustMapVOs) {
+ List groups = new ArrayList<>();
+ for (LdapTrustMapVO vo : ldapTrustMapVOs) {
+ groups.add(vo.getName());
+ }
+ return groups;
+ }
+
+ /**
+ * checks if the user exists in ldap and create in cloudstack if needed
+ * @param username login id
+ * @param password pass phrase
+ * @param domainId domain the user is trying to log on to
+ * @param user cloudstack user object
+ * @param ldapTrustMapVO the trust mapping for the domain to the ldap group
+ * @return false if the ldap user object does not exist or authenitication fails
+ */
+ private Pair authenticate(String username, String password, Long domainId, UserAccount user, LdapTrustMapVO ldapTrustMapVO) {
+ Pair rc = new Pair(false, null);
+ try {
+ LdapUser ldapUser = _ldapManager.getUser(username, ldapTrustMapVO.getType().toString(), ldapTrustMapVO.getName(), domainId);
+ final short accountType = ldapTrustMapVO.getAccountType();
+ processLdapUser(password, domainId, user, rc, ldapUser, accountType);
+ } catch (NoLdapUserMatchingQueryException e) {
+ s_logger.debug(e.getMessage());
+ }
+ return rc;
+ }
+
+ private void processLdapUser(String password, Long domainId, UserAccount user, Pair rc, LdapUser ldapUser, short accountType) {
+ if(!ldapUser.isDisabled()) {
+ rc.first(_ldapManager.canAuthenticate(ldapUser.getPrincipal(), password, domainId));
+ if(rc.first()) {
+ if(user == null) {
+ // import user to cloudstack
+ createCloudStackUserAccount(ldapUser, domainId, accountType);
+ } else {
+ enableUserInCloudStack(user);
+ }
+ } else if(user != null) {
+ rc.second(ActionOnFailedAuthentication.INCREMENT_INCORRECT_LOGIN_ATTEMPT_COUNT);
+ }
+ } else {
+ //disable user in cloudstack
+ disableUserInCloudStack(user);
+ }
+ }
+
+ /**
+ * checks if the user is configured both in ldap and in cloudstack.
+ * @param username login id
+ * @param password pass phrase
+ * @param domainId domain the user is trying to log on to
+ * @param user cloudstack user object
+ * @return false if either user object does not exist or authenitication fails
+ */
+ private Pair authenticate(String username, String password, Long domainId, UserAccount user) {
+ boolean result = false;
+
+ if(user != null ) {
+ try {
+ LdapUser ldapUser = _ldapManager.getUser(username, domainId);
+ if(!ldapUser.isDisabled()) {
+ result = _ldapManager.canAuthenticate(ldapUser.getPrincipal(), password, domainId);
+ } else {
+ s_logger.debug("user with principal "+ ldapUser.getPrincipal() + " is disabled in ldap");
+ }
+ } catch (NoLdapUserMatchingQueryException e) {
+ s_logger.debug(e.getMessage());
+ }
+ }
+ return (!result && user != null) ?
+ new Pair(false, ActionOnFailedAuthentication.INCREMENT_INCORRECT_LOGIN_ATTEMPT_COUNT):
+ new Pair(false, null);
}
private void enableUserInCloudStack(UserAccount user) {
@@ -131,6 +254,12 @@ public class LdapAuthenticator extends AdapterBase implements UserAuthenticator
}
}
+ private void removeUserInCloudStack(UserAccount user) {
+ if (user != null) {
+ _accountManager.disableUser(user.getId());
+ }
+ }
+
@Override
public String encode(final String password) {
return password;
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapConfiguration.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapConfiguration.java
index 56b39a8b3d1..22f8abc9aa5 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapConfiguration.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapConfiguration.java
@@ -31,75 +31,215 @@ import org.apache.cloudstack.ldap.dao.LdapConfigurationDao;
public class LdapConfiguration implements Configurable{
private final static String factory = "com.sun.jndi.ldap.LdapCtxFactory";
- private static final ConfigKey ldapReadTimeout = new ConfigKey(Long.class, "ldap.read.timeout", "Advanced", "1000",
- "LDAP connection Timeout in milli sec", true, ConfigKey.Scope.Global, 1l);
+ private static final ConfigKey ldapReadTimeout = new ConfigKey(
+ Long.class,
+ "ldap.read.timeout",
+ "Advanced",
+ "1000",
+ "LDAP connection Timeout in milli sec",
+ true,
+ ConfigKey.Scope.Domain,
+ 1l);
- private static final ConfigKey ldapPageSize = new ConfigKey(Integer.class, "ldap.request.page.size", "Advanced", "1000",
- "page size sent to ldap server on each request to get user", true, ConfigKey.Scope.Global, 1);
- private static final ConfigKey ldapProvider = new ConfigKey(String.class, "ldap.provider", "Advanced", "openldap", "ldap provider ex:openldap, microsoftad",
- true, ConfigKey.Scope.Global, null);
+ private static final ConfigKey ldapPageSize = new ConfigKey(
+ Integer.class,
+ "ldap.request.page.size",
+ "Advanced",
+ "1000",
+ "page size sent to ldap server on each request to get user",
+ true,
+ ConfigKey.Scope.Domain,
+ 1);
- private static final ConfigKey ldapEnableNestedGroups = new ConfigKey(Boolean.class, "ldap.nested.groups.enable", "Advanced", "true",
- "if true, nested groups will also be queried", true, ConfigKey.Scope.Global, null);
+ private static final ConfigKey ldapEnableNestedGroups = new ConfigKey(
+ "Advanced",
+ Boolean.class,
+ "ldap.nested.groups.enable",
+ "true",
+ "if true, nested groups will also be queried",
+ true,
+ ConfigKey.Scope.Domain);
+
+ private static final ConfigKey ldapMemberOfAttribute = new ConfigKey(
+ "Advanced",
+ String.class,
+ "ldap.user.memberof.attribute",
+ "memberof",
+ "the reverse membership attibute for group members",
+ true,
+ ConfigKey.Scope.Domain);
+
+ private static final ConfigKey ldapProvider = new ConfigKey(
+ "Advanced",
+ String.class,
+ "ldap.provider",
+ "openldap",
+ "ldap provider ex:openldap, microsoftad",
+ true,
+ ConfigKey.Scope.Domain);
+
+ private static final ConfigKey ldapBaseDn = new ConfigKey(
+ "Advanced",
+ String.class,
+ "ldap.basedn",
+ null,
+ "Sets the basedn for LDAP",
+ true,
+ ConfigKey.Scope.Domain);
+
+ private static final ConfigKey ldapBindPassword = new ConfigKey(
+ "Advanced",
+ String.class,
+ "ldap.bind.password",
+ null,
+ "Sets the bind password for LDAP",
+ true,
+ ConfigKey.Scope.Domain);
+ private static final ConfigKey ldapBindPrincipal = new ConfigKey(
+ "Advanced",
+ String.class,
+ "ldap.bind.principal",
+ null,
+ "Sets the bind principal for LDAP",
+ true,
+ ConfigKey.Scope.Domain);
+ private static final ConfigKey ldapEmailAttribute = new ConfigKey(
+ "Advanced",
+ String.class,
+ "ldap.email.attribute",
+ "mail",
+ "Sets the email attribute used within LDAP",
+ true,
+ ConfigKey.Scope.Domain);
+ private static final ConfigKey ldapFirstnameAttribute = new ConfigKey(
+ "Advanced",
+ String.class,
+ "ldap.firstname.attribute",
+ "givenname",
+ "Sets the firstname attribute used within LDAP",
+ true,
+ ConfigKey.Scope.Domain);
+ private static final ConfigKey ldapLastnameAttribute = new ConfigKey(
+ "Advanced",
+ String.class, "ldap.lastname.attribute",
+ "sn",
+ "Sets the lastname attribute used within LDAP",
+ true,
+ ConfigKey.Scope.Domain);
+ private static final ConfigKey ldapUsernameAttribute = new ConfigKey(
+ "Advanced",
+ String.class,
+ "ldap.username.attribute",
+ "uid",
+ "Sets the username attribute used within LDAP",
+ true,
+ ConfigKey.Scope.Domain);
+ private static final ConfigKey ldapUserObject = new ConfigKey(
+ "Advanced",
+ String.class,
+ "ldap.user.object",
+ "inetOrgPerson",
+ "Sets the object type of users within LDAP",
+ true,
+ ConfigKey.Scope.Domain);
+ private static final ConfigKey ldapSearchGroupPrinciple = new ConfigKey(
+ "Advanced",
+ String.class,
+ "ldap.search.group.principle",
+ null,
+ "Sets the principle of the group that users must be a member of",
+ true,
+ ConfigKey.Scope.Domain);
+ private static final ConfigKey ldapGroupObject = new ConfigKey(
+ "Advanced",
+ String.class,
+ "ldap.group.object",
+ "groupOfUniqueNames",
+ "Sets the object type of groups within LDAP",
+ true,
+ ConfigKey.Scope.Domain);
+ private static final ConfigKey ldapGroupUniqueMemberAttribute = new ConfigKey(
+ "Advanced",
+ String.class,
+ "ldap.group.user.uniquemember",
+ "uniquemember",
+ "Sets the attribute for uniquemembers within a group",
+ true,
+ ConfigKey.Scope.Domain);
+
+ private static final ConfigKey ldapTrustStore = new ConfigKey(
+ "Advanced",
+ String.class,
+ "ldap.truststore",
+ null,
+ "Sets the path to the truststore to use for SSL",
+ true,
+ ConfigKey.Scope.Domain);
+ private static final ConfigKey ldapTrustStorePassword = new ConfigKey(
+ "Advanced",
+ String.class,
+ "ldap.truststore.password",
+ null,
+ "Sets the password for the truststore",
+ true,
+ ConfigKey.Scope.Domain);
private final static int scope = SearchControls.SUBTREE_SCOPE;
- @Inject
- private ConfigurationDao _configDao;
-
@Inject
private LdapConfigurationDao _ldapConfigurationDao;
public LdapConfiguration() {
}
- public LdapConfiguration(final ConfigurationDao configDao, final LdapConfigurationDao ldapConfigurationDao) {
- _configDao = configDao;
+ public LdapConfiguration(final LdapConfigurationDao ldapConfigurationDao) {
_ldapConfigurationDao = ldapConfigurationDao;
}
- public String getAuthentication() {
- if ((getBindPrincipal() == null) && (getBindPassword() == null)) {
+ @Deprecated
+ public LdapConfiguration(final ConfigurationDao configDao, final LdapConfigurationDao ldapConfigurationDao) {
+ _ldapConfigurationDao = ldapConfigurationDao;
+ }
+
+ public String getAuthentication(final Long domainId) {
+ if ((getBindPrincipal(domainId) == null) && (getBindPassword(domainId) == null)) {
return "none";
} else {
return "simple";
}
}
- public String getBaseDn() {
- return _configDao.getValue("ldap.basedn");
+ public String getBaseDn(final Long domainId) {
+ return ldapBaseDn.valueIn(domainId);
}
- public String getBindPassword() {
- return _configDao.getValue("ldap.bind.password");
+ public String getBindPassword(final Long domainId) {
+ return ldapBindPassword.valueIn(domainId);
}
- public String getBindPrincipal() {
- return _configDao.getValue("ldap.bind.principal");
+ public String getBindPrincipal(final Long domainId) {
+ return ldapBindPrincipal.valueIn(domainId);
}
- public String getEmailAttribute() {
- final String emailAttribute = _configDao.getValue("ldap.email.attribute");
- return emailAttribute == null ? "mail" : emailAttribute;
+ public String getEmailAttribute(final Long domainId) {
+ return ldapEmailAttribute.valueIn(domainId);
}
public String getFactory() {
return factory;
}
- public String getFirstnameAttribute() {
- final String firstnameAttribute = _configDao.getValue("ldap.firstname.attribute");
- return firstnameAttribute == null ? "givenname" : firstnameAttribute;
+ public String getFirstnameAttribute(final Long domainId) {
+ return ldapFirstnameAttribute.valueIn(domainId);
}
- public String getLastnameAttribute() {
- final String lastnameAttribute = _configDao.getValue("ldap.lastname.attribute");
- return lastnameAttribute == null ? "sn" : lastnameAttribute;
+ public String getLastnameAttribute(final Long domainId) {
+ return ldapLastnameAttribute.valueIn(domainId);
}
- public String getProviderUrl() {
+ public String getProviderUrl(final Long domainId) {
final String protocol = getSSLStatus() == true ? "ldaps://" : "ldap://";
- final Pair, Integer> result = _ldapConfigurationDao.searchConfigurations(null, 0);
+ final Pair, Integer> result = _ldapConfigurationDao.searchConfigurations(null, 0, domainId);
final StringBuilder providerUrls = new StringBuilder();
String delim = "";
for (final LdapConfigurationVO resource : result.first()) {
@@ -110,17 +250,24 @@ public class LdapConfiguration implements Configurable{
return providerUrls.toString();
}
- public String[] getReturnAttributes() {
- return new String[] {getUsernameAttribute(), getEmailAttribute(), getFirstnameAttribute(), getLastnameAttribute(), getCommonNameAttribute(),
- getUserAccountControlAttribute()};
+ public String[] getReturnAttributes(final Long domainId) {
+ return new String[] {
+ getUsernameAttribute(domainId),
+ getEmailAttribute(domainId),
+ getFirstnameAttribute(domainId),
+ getLastnameAttribute(domainId),
+ getCommonNameAttribute(),
+ getUserAccountControlAttribute(),
+ getUserMemberOfAttribute(domainId)
+ };
}
public int getScope() {
return scope;
}
- public String getSearchGroupPrinciple() {
- return _configDao.getValue("ldap.search.group.principle");
+ public String getSearchGroupPrinciple(final Long domainId) {
+ return ldapSearchGroupPrinciple.valueIn(domainId);
}
public boolean getSSLStatus() {
@@ -132,53 +279,51 @@ public class LdapConfiguration implements Configurable{
}
public String getTrustStore() {
- return _configDao.getValue("ldap.truststore");
+ return ldapTrustStore.value();
}
public String getTrustStorePassword() {
- return _configDao.getValue("ldap.truststore.password");
+ return ldapTrustStorePassword.value();
}
- public String getUsernameAttribute() {
- final String usernameAttribute = _configDao.getValue("ldap.username.attribute");
- return usernameAttribute == null ? "uid" : usernameAttribute;
+ public String getUsernameAttribute(final Long domainId) {
+ return ldapUsernameAttribute.valueIn(domainId);
}
- public String getUserObject() {
- final String userObject = _configDao.getValue("ldap.user.object");
- return userObject == null ? "inetOrgPerson" : userObject;
+ public String getUserObject(final Long domainId) {
+ return ldapUserObject.valueIn(domainId);
}
- public String getGroupObject() {
- final String groupObject = _configDao.getValue("ldap.group.object");
- return groupObject == null ? "groupOfUniqueNames" : groupObject;
+ public String getGroupObject(final Long domainId) {
+ return ldapGroupObject.valueIn(domainId);
}
- public String getGroupUniqueMemeberAttribute() {
- final String uniqueMemberAttribute = _configDao.getValue("ldap.group.user.uniquemember");
- return uniqueMemberAttribute == null ? "uniquemember" : uniqueMemberAttribute;
+ public String getGroupUniqueMemberAttribute(final Long domainId) {
+ return ldapGroupUniqueMemberAttribute.valueIn(domainId);
}
+ // TODO remove hard-coding
public String getCommonNameAttribute() {
return "cn";
}
+ // TODO remove hard-coding
public String getUserAccountControlAttribute() {
return "userAccountControl";
}
- public Long getReadTimeout() {
- return ldapReadTimeout.value();
+ public Long getReadTimeout(final Long domainId) {
+ return ldapReadTimeout.valueIn(domainId);
}
- public Integer getLdapPageSize() {
- return ldapPageSize.value();
+ public Integer getLdapPageSize(final Long domainId) {
+ return ldapPageSize.valueIn(domainId);
}
- public LdapUserManager.Provider getLdapProvider() {
+ public LdapUserManager.Provider getLdapProvider(final Long domainId) {
LdapUserManager.Provider provider;
try {
- provider = LdapUserManager.Provider.valueOf(ldapProvider.value().toUpperCase());
+ provider = LdapUserManager.Provider.valueOf(ldapProvider.valueIn(domainId).toUpperCase());
} catch (IllegalArgumentException ex) {
//openldap is the default
provider = LdapUserManager.Provider.OPENLDAP;
@@ -186,8 +331,12 @@ public class LdapConfiguration implements Configurable{
return provider;
}
- public boolean isNestedGroupsEnabled() {
- return ldapEnableNestedGroups.value();
+ public boolean isNestedGroupsEnabled(final Long domainId) {
+ return ldapEnableNestedGroups.valueIn(domainId);
+ }
+
+ public static String getUserMemberOfAttribute(final Long domainId) {
+ return ldapMemberOfAttribute.valueIn(domainId);
}
@Override
@@ -197,6 +346,25 @@ public class LdapConfiguration implements Configurable{
@Override
public ConfigKey>[] getConfigKeys() {
- return new ConfigKey>[] {ldapReadTimeout, ldapPageSize, ldapProvider, ldapEnableNestedGroups};
+ return new ConfigKey>[]{
+ ldapReadTimeout,
+ ldapPageSize,
+ ldapProvider,
+ ldapEnableNestedGroups,
+ ldapBaseDn,
+ ldapBindPassword,
+ ldapBindPrincipal,
+ ldapEmailAttribute,
+ ldapFirstnameAttribute,
+ ldapLastnameAttribute,
+ ldapUsernameAttribute,
+ ldapUserObject,
+ ldapSearchGroupPrinciple,
+ ldapGroupObject,
+ ldapGroupUniqueMemberAttribute,
+ ldapTrustStore,
+ ldapTrustStorePassword,
+ ldapMemberOfAttribute
+ };
}
-}
\ No newline at end of file
+}
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapConfigurationVO.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapConfigurationVO.java
index 488e7f44485..e7db88675ab 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapConfigurationVO.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapConfigurationVO.java
@@ -39,12 +39,16 @@ public class LdapConfigurationVO implements InternalIdentity {
@Column(name = "port")
private int port;
+ @Column(name = "domain_id")
+ private Long domainId;
+
public LdapConfigurationVO() {
}
- public LdapConfigurationVO(final String hostname, final int port) {
+ public LdapConfigurationVO(final String hostname, final int port, final Long domainId) {
this.hostname = hostname;
this.port = port;
+ this.domainId = domainId;
}
public String getHostname() {
@@ -60,6 +64,10 @@ public class LdapConfigurationVO implements InternalIdentity {
return port;
}
+ public Long getDomainId() {
+ return domainId;
+ }
+
public void setId(final long id) {
this.id = id;
}
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapContextFactory.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapContextFactory.java
index 9e27fff078e..b141f053008 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapContextFactory.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapContextFactory.java
@@ -40,29 +40,31 @@ public class LdapContextFactory {
_ldapConfiguration = ldapConfiguration;
}
- public LdapContext createBindContext() throws NamingException, IOException {
- return createBindContext(null);
+ // TODO add optional domain (optional only for backwards compatibility)
+ public LdapContext createBindContext(Long domainId) throws NamingException, IOException {
+ return createBindContext(null, domainId);
}
- public LdapContext createBindContext(final String providerUrl) throws NamingException, IOException {
- final String bindPrincipal = _ldapConfiguration.getBindPrincipal();
- final String bindPassword = _ldapConfiguration.getBindPassword();
- return createInitialDirContext(bindPrincipal, bindPassword, providerUrl, true);
+ // TODO add optional domain (optional only for backwards compatibility)
+ public LdapContext createBindContext(final String providerUrl, Long domainId) throws NamingException, IOException {
+ final String bindPrincipal = _ldapConfiguration.getBindPrincipal(domainId);
+ final String bindPassword = _ldapConfiguration.getBindPassword(domainId);
+ return createInitialDirContext(bindPrincipal, bindPassword, providerUrl, true, domainId);
}
- private LdapContext createInitialDirContext(final String principal, final String password, final boolean isSystemContext) throws NamingException, IOException {
- return createInitialDirContext(principal, password, null, isSystemContext);
+ private LdapContext createInitialDirContext(final String principal, final String password, final boolean isSystemContext, Long domainId) throws NamingException, IOException {
+ return createInitialDirContext(principal, password, null, isSystemContext, domainId);
}
- private LdapContext createInitialDirContext(final String principal, final String password, final String providerUrl, final boolean isSystemContext)
+ private LdapContext createInitialDirContext(final String principal, final String password, final String providerUrl, final boolean isSystemContext, Long domainId)
throws NamingException, IOException {
- Hashtable environment = getEnvironment(principal, password, providerUrl, isSystemContext);
+ Hashtable environment = getEnvironment(principal, password, providerUrl, isSystemContext, domainId);
s_logger.debug("initializing ldap with provider url: " + environment.get(Context.PROVIDER_URL));
return new InitialLdapContext(environment, null);
}
- public LdapContext createUserContext(final String principal, final String password) throws NamingException, IOException {
- return createInitialDirContext(principal, password, false);
+ public LdapContext createUserContext(final String principal, final String password, Long domainId) throws NamingException, IOException {
+ return createInitialDirContext(principal, password, false, domainId);
}
private void enableSSL(final Hashtable environment) {
@@ -76,19 +78,19 @@ public class LdapContextFactory {
}
}
- private Hashtable getEnvironment(final String principal, final String password, final String providerUrl, final boolean isSystemContext) {
+ private Hashtable getEnvironment(final String principal, final String password, final String providerUrl, final boolean isSystemContext, Long domainId) {
final String factory = _ldapConfiguration.getFactory();
- final String url = providerUrl == null ? _ldapConfiguration.getProviderUrl() : providerUrl;
+ final String url = providerUrl == null ? _ldapConfiguration.getProviderUrl(domainId) : providerUrl;
final Hashtable environment = new Hashtable();
environment.put(Context.INITIAL_CONTEXT_FACTORY, factory);
environment.put(Context.PROVIDER_URL, url);
- environment.put("com.sun.jndi.ldap.read.timeout", _ldapConfiguration.getReadTimeout().toString());
+ environment.put("com.sun.jndi.ldap.read.timeout", _ldapConfiguration.getReadTimeout(domainId).toString());
environment.put("com.sun.jndi.ldap.connect.pool", "true");
enableSSL(environment);
- setAuthentication(environment, isSystemContext);
+ setAuthentication(environment, isSystemContext, domainId);
if (principal != null) {
environment.put(Context.SECURITY_PRINCIPAL, principal);
@@ -101,8 +103,8 @@ public class LdapContextFactory {
return environment;
}
- private void setAuthentication(final Hashtable environment, final boolean isSystemContext) {
- final String authentication = _ldapConfiguration.getAuthentication();
+ private void setAuthentication(final Hashtable environment, final boolean isSystemContext, final Long domainId) {
+ final String authentication = _ldapConfiguration.getAuthentication(domainId);
if ("none".equals(authentication) && !isSystemContext) {
environment.put(Context.SECURITY_AUTHENTICATION, "simple");
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapManager.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapManager.java
index 6af2c4ebd95..002242c8f02 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapManager.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapManager.java
@@ -18,36 +18,48 @@ package org.apache.cloudstack.ldap;
import java.util.List;
+import org.apache.cloudstack.api.command.LdapAddConfigurationCmd;
+import org.apache.cloudstack.api.command.LdapDeleteConfigurationCmd;
import org.apache.cloudstack.api.command.LdapListConfigurationCmd;
+import org.apache.cloudstack.api.command.LinkAccountToLdapCmd;
+import org.apache.cloudstack.api.command.LinkDomainToLdapCmd;
import org.apache.cloudstack.api.response.LdapConfigurationResponse;
import org.apache.cloudstack.api.response.LdapUserResponse;
import com.cloud.exception.InvalidParameterValueException;
import com.cloud.utils.Pair;
import com.cloud.utils.component.PluggableService;
+import org.apache.cloudstack.api.response.LinkAccountToLdapResponse;
import org.apache.cloudstack.api.response.LinkDomainToLdapResponse;
public interface LdapManager extends PluggableService {
enum LinkType { GROUP, OU;}
- LdapConfigurationResponse addConfiguration(String hostname, int port) throws InvalidParameterValueException;
+ LdapConfigurationResponse addConfiguration(final LdapAddConfigurationCmd cmd) throws InvalidParameterValueException;
- boolean canAuthenticate(String principal, String password);
+ @Deprecated
+ LdapConfigurationResponse addConfiguration(String hostname, int port, Long domainId) throws InvalidParameterValueException;
+
+ boolean canAuthenticate(String principal, String password, final Long domainId);
LdapConfigurationResponse createLdapConfigurationResponse(LdapConfigurationVO configuration);
LdapUserResponse createLdapUserResponse(LdapUser user);
- LdapConfigurationResponse deleteConfiguration(String hostname) throws InvalidParameterValueException;
+ LdapConfigurationResponse deleteConfiguration(LdapDeleteConfigurationCmd cmd) throws InvalidParameterValueException;
- LdapUser getUser(final String username) throws NoLdapUserMatchingQueryException;
+ @Deprecated
+ LdapConfigurationResponse deleteConfiguration(String hostname, int port, Long domainId) throws InvalidParameterValueException;
- LdapUser getUser(String username, String type, String name) throws NoLdapUserMatchingQueryException;
+ // TODO username is only unique withing domain scope (add domain id to call)
+ LdapUser getUser(final String username, Long domainId) throws NoLdapUserMatchingQueryException;
- List getUsers() throws NoLdapUserMatchingQueryException;
+ LdapUser getUser(String username, String type, String name, Long domainId) throws NoLdapUserMatchingQueryException;
- List getUsersInGroup(String groupName) throws NoLdapUserMatchingQueryException;
+ List getUsers(Long domainId) throws NoLdapUserMatchingQueryException;
+
+ List getUsersInGroup(String groupName, Long domainId) throws NoLdapUserMatchingQueryException;
boolean isLdapEnabled();
@@ -55,7 +67,15 @@ public interface LdapManager extends PluggableService {
List searchUsers(String query) throws NoLdapUserMatchingQueryException;
- LinkDomainToLdapResponse linkDomainToLdap(Long domainId, String type, String name, short accountType);
+ LinkDomainToLdapResponse linkDomainToLdap(LinkDomainToLdapCmd cmd);
- public LdapTrustMapVO getDomainLinkedToLdap(long domainId);
+ LdapTrustMapVO getDomainLinkedToLdap(long domainId);
+
+ List getDomainLinkage(long domainId);
+
+ LdapTrustMapVO getAccountLinkedToLdap(long domainId, long accountId);
+
+ LdapTrustMapVO getLinkedLdapGroup(long domainId, String group);
+
+ LinkAccountToLdapResponse linkAccountToLdap(LinkAccountToLdapCmd linkAccountToLdapCmd);
}
\ No newline at end of file
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapManagerImpl.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapManagerImpl.java
index beb7a61cd70..b82231c99d7 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapManagerImpl.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapManagerImpl.java
@@ -23,6 +23,7 @@ import java.util.List;
import javax.inject.Inject;
import javax.naming.NamingException;
import javax.naming.ldap.LdapContext;
+import java.util.UUID;
import org.apache.cloudstack.api.LdapValidator;
import org.apache.cloudstack.api.command.LDAPConfigCmd;
@@ -34,9 +35,11 @@ import org.apache.cloudstack.api.command.LdapImportUsersCmd;
import org.apache.cloudstack.api.command.LdapListConfigurationCmd;
import org.apache.cloudstack.api.command.LdapListUsersCmd;
import org.apache.cloudstack.api.command.LdapUserSearchCmd;
+import org.apache.cloudstack.api.command.LinkAccountToLdapCmd;
import org.apache.cloudstack.api.command.LinkDomainToLdapCmd;
import org.apache.cloudstack.api.response.LdapConfigurationResponse;
import org.apache.cloudstack.api.response.LdapUserResponse;
+import org.apache.cloudstack.api.response.LinkAccountToLdapResponse;
import org.apache.cloudstack.api.response.LinkDomainToLdapResponse;
import org.apache.cloudstack.ldap.dao.LdapConfigurationDao;
import org.apache.cloudstack.ldap.dao.LdapTrustMapDao;
@@ -47,6 +50,9 @@ import org.springframework.stereotype.Component;
import com.cloud.domain.DomainVO;
import com.cloud.domain.dao.DomainDao;
import com.cloud.exception.InvalidParameterValueException;
+import com.cloud.user.Account;
+import com.cloud.user.AccountVO;
+import com.cloud.user.dao.AccountDao;
import com.cloud.utils.Pair;
@Component
@@ -59,6 +65,9 @@ public class LdapManagerImpl implements LdapManager, LdapValidator {
@Inject
private DomainDao domainDao;
+ @Inject
+ private AccountDao accountDao;
+
@Inject
private LdapContextFactory _ldapContextFactory;
@@ -85,17 +94,32 @@ public class LdapManagerImpl implements LdapManager, LdapValidator {
}
@Override
- public LdapConfigurationResponse addConfiguration(final String hostname, final int port) throws InvalidParameterValueException {
- LdapConfigurationVO configuration = _ldapConfigurationDao.findByHostname(hostname);
+ public LdapConfigurationResponse addConfiguration(final LdapAddConfigurationCmd cmd) throws InvalidParameterValueException {
+ return addConfigurationInternal(cmd.getHostname(),cmd.getPort(),cmd.getDomainId());
+ }
+
+ @Override // TODO make private
+ public LdapConfigurationResponse addConfiguration(final String hostname, int port, final Long domainId) throws InvalidParameterValueException {
+ return addConfigurationInternal(hostname,port,domainId);
+ }
+
+ private LdapConfigurationResponse addConfigurationInternal(final String hostname, int port, final Long domainId) throws InvalidParameterValueException {
+ // TODO evaluate what the right default should be
+ if(port <= 0) {
+ port = 389;
+ }
+
+ // hostname:port is unique for domain binding
+ LdapConfigurationVO configuration = _ldapConfigurationDao.find(hostname, port, domainId);
if (configuration == null) {
LdapContext context = null;
try {
final String providerUrl = "ldap://" + hostname + ":" + port;
- context = _ldapContextFactory.createBindContext(providerUrl);
- configuration = new LdapConfigurationVO(hostname, port);
+ context = _ldapContextFactory.createBindContext(providerUrl,domainId);
+ configuration = new LdapConfigurationVO(hostname, port, domainId);
_ldapConfigurationDao.persist(configuration);
- s_logger.info("Added new ldap server with hostname: " + hostname);
- return new LdapConfigurationResponse(hostname, port);
+ s_logger.info("Added new ldap server with url: " + providerUrl + (domainId == null ? "": " for domain " + domainId));
+ return createLdapConfigurationResponse(configuration);
} catch (NamingException | IOException e) {
s_logger.debug("NamingException while doing an LDAP bind", e);
throw new InvalidParameterValueException("Unable to bind to the given LDAP server");
@@ -107,10 +131,18 @@ public class LdapManagerImpl implements LdapManager, LdapValidator {
}
}
+ /**
+ * TODO decide if the principal is good enough to get the domain id or we need to add it as parameter
+ * @param principal
+ * @param password
+ * @param domainId
+ * @return
+ */
@Override
- public boolean canAuthenticate(final String principal, final String password) {
+ public boolean canAuthenticate(final String principal, final String password, final Long domainId) {
try {
- final LdapContext context = _ldapContextFactory.createUserContext(principal, password);
+ // TODO return the right account for this user
+ final LdapContext context = _ldapContextFactory.createUserContext(principal, password,domainId);
closeContext(context);
return true;
} catch (NamingException | IOException e) {
@@ -132,10 +164,11 @@ public class LdapManagerImpl implements LdapManager, LdapValidator {
@Override
public LdapConfigurationResponse createLdapConfigurationResponse(final LdapConfigurationVO configuration) {
- final LdapConfigurationResponse response = new LdapConfigurationResponse();
- response.setHostname(configuration.getHostname());
- response.setPort(configuration.getPort());
- return response;
+ String domainUuid = null;
+ if(configuration.getDomainId() != null) {
+ domainUuid = domainDao.findById(configuration.getDomainId()).getUuid();
+ }
+ return new LdapConfigurationResponse(configuration.getHostname(), configuration.getPort(), domainUuid);
}
@Override
@@ -151,14 +184,23 @@ public class LdapManagerImpl implements LdapManager, LdapValidator {
}
@Override
- public LdapConfigurationResponse deleteConfiguration(final String hostname) throws InvalidParameterValueException {
- final LdapConfigurationVO configuration = _ldapConfigurationDao.findByHostname(hostname);
+ public LdapConfigurationResponse deleteConfiguration(final LdapDeleteConfigurationCmd cmd) throws InvalidParameterValueException {
+ return deleteConfigurationInternal(cmd.getHostname(), cmd.getPort(), cmd.getDomainId());
+ }
+
+ @Override
+ public LdapConfigurationResponse deleteConfiguration(final String hostname, int port, Long domainId) throws InvalidParameterValueException {
+ return deleteConfigurationInternal(hostname, port, domainId);
+ }
+
+ private LdapConfigurationResponse deleteConfigurationInternal(final String hostname, int port, Long domainId) throws InvalidParameterValueException {
+ final LdapConfigurationVO configuration = _ldapConfigurationDao.find(hostname,port,domainId);
if (configuration == null) {
throw new InvalidParameterValueException("Cannot find configuration with hostname " + hostname);
} else {
_ldapConfigurationDao.remove(configuration.getId());
- s_logger.info("Removed ldap server with hostname: " + hostname);
- return new LdapConfigurationResponse(configuration.getHostname(), configuration.getPort());
+ s_logger.info("Removed ldap server with url: " + hostname + ':' + port + (domainId == null ? "" : " for domain id " + domainId));
+ return createLdapConfigurationResponse(configuration);
}
}
@@ -175,17 +217,18 @@ public class LdapManagerImpl implements LdapManager, LdapValidator {
cmdList.add(LDAPConfigCmd.class);
cmdList.add(LDAPRemoveCmd.class);
cmdList.add(LinkDomainToLdapCmd.class);
+ cmdList.add(LinkAccountToLdapCmd.class);
return cmdList;
}
@Override
- public LdapUser getUser(final String username) throws NoLdapUserMatchingQueryException {
+ public LdapUser getUser(final String username, Long domainId) throws NoLdapUserMatchingQueryException {
LdapContext context = null;
try {
- context = _ldapContextFactory.createBindContext();
+ context = _ldapContextFactory.createBindContext(domainId);
final String escapedUsername = LdapUtils.escapeLDAPSearchFilter(username);
- return _ldapUserManagerFactory.getInstance(_ldapConfiguration.getLdapProvider()).getUser(escapedUsername, context);
+ return _ldapUserManagerFactory.getInstance(_ldapConfiguration.getLdapProvider(null)).getUser(escapedUsername, context, domainId);
} catch (NamingException | IOException e) {
s_logger.debug("ldap Exception: ",e);
@@ -196,26 +239,26 @@ public class LdapManagerImpl implements LdapManager, LdapValidator {
}
@Override
- public LdapUser getUser(final String username, final String type, final String name) throws NoLdapUserMatchingQueryException {
+ public LdapUser getUser(final String username, final String type, final String name, Long domainId) throws NoLdapUserMatchingQueryException {
LdapContext context = null;
try {
- context = _ldapContextFactory.createBindContext();
+ context = _ldapContextFactory.createBindContext(domainId);
final String escapedUsername = LdapUtils.escapeLDAPSearchFilter(username);
- return _ldapUserManagerFactory.getInstance(_ldapConfiguration.getLdapProvider()).getUser(escapedUsername, type, name, context);
+ return _ldapUserManagerFactory.getInstance(_ldapConfiguration.getLdapProvider(null)).getUser(escapedUsername, type, name, context, domainId);
} catch (NamingException | IOException e) {
s_logger.debug("ldap Exception: ",e);
- throw new NoLdapUserMatchingQueryException("No Ldap User found for username: "+username + "name: " + name + "of type: " + type);
+ throw new NoLdapUserMatchingQueryException("No Ldap User found for username: "+username + " in group: " + name + " of type: " + type);
} finally {
closeContext(context);
}
}
@Override
- public List getUsers() throws NoLdapUserMatchingQueryException {
+ public List getUsers(Long domainId) throws NoLdapUserMatchingQueryException {
LdapContext context = null;
try {
- context = _ldapContextFactory.createBindContext();
- return _ldapUserManagerFactory.getInstance(_ldapConfiguration.getLdapProvider()).getUsers(context);
+ context = _ldapContextFactory.createBindContext(domainId);
+ return _ldapUserManagerFactory.getInstance(_ldapConfiguration.getLdapProvider(domainId)).getUsers(context, domainId);
} catch (NamingException | IOException e) {
s_logger.debug("ldap Exception: ",e);
throw new NoLdapUserMatchingQueryException("*");
@@ -225,11 +268,11 @@ public class LdapManagerImpl implements LdapManager, LdapValidator {
}
@Override
- public List getUsersInGroup(String groupName) throws NoLdapUserMatchingQueryException {
+ public List getUsersInGroup(String groupName, Long domainId) throws NoLdapUserMatchingQueryException {
LdapContext context = null;
try {
- context = _ldapContextFactory.createBindContext();
- return _ldapUserManagerFactory.getInstance(_ldapConfiguration.getLdapProvider()).getUsersInGroup(groupName, context);
+ context = _ldapContextFactory.createBindContext(domainId);
+ return _ldapUserManagerFactory.getInstance(_ldapConfiguration.getLdapProvider(domainId)).getUsersInGroup(groupName, context, domainId);
} catch (NamingException | IOException e) {
s_logger.debug("ldap NamingException: ",e);
throw new NoLdapUserMatchingQueryException("groupName=" + groupName);
@@ -247,7 +290,8 @@ public class LdapManagerImpl implements LdapManager, LdapValidator {
public Pair, Integer> listConfigurations(final LdapListConfigurationCmd cmd) {
final String hostname = cmd.getHostname();
final int port = cmd.getPort();
- final Pair, Integer> result = _ldapConfigurationDao.searchConfigurations(hostname, port);
+ final Long domainId = cmd.getDomainId();
+ final Pair, Integer> result = _ldapConfigurationDao.searchConfigurations(hostname, port, domainId);
return new Pair, Integer>(result.first(), result.second());
}
@@ -255,9 +299,10 @@ public class LdapManagerImpl implements LdapManager, LdapValidator {
public List searchUsers(final String username) throws NoLdapUserMatchingQueryException {
LdapContext context = null;
try {
- context = _ldapContextFactory.createBindContext();
+ // TODO search users per domain (only?)
+ context = _ldapContextFactory.createBindContext(null);
final String escapedUsername = LdapUtils.escapeLDAPSearchFilter(username);
- return _ldapUserManagerFactory.getInstance(_ldapConfiguration.getLdapProvider()).getUsers("*" + escapedUsername + "*", context);
+ return _ldapUserManagerFactory.getInstance(_ldapConfiguration.getLdapProvider(null)).getUsers("*" + escapedUsername + "*", context, null);
} catch (NamingException | IOException e) {
s_logger.debug("ldap Exception: ",e);
throw new NoLdapUserMatchingQueryException(username);
@@ -267,14 +312,20 @@ public class LdapManagerImpl implements LdapManager, LdapValidator {
}
@Override
- public LinkDomainToLdapResponse linkDomainToLdap(Long domainId, String type, String name, short accountType) {
+ public LinkDomainToLdapResponse linkDomainToLdap(LinkDomainToLdapCmd cmd) {
+ Validate.isTrue(_ldapConfiguration.getBaseDn(cmd.getDomainId()) == null, "can not configure an ldap server and an ldap group/ou to a domain");
+ Validate.notEmpty(cmd.getLdapDomain(), "ldapDomain cannot be empty, please supply a GROUP or OU name");
+ return linkDomainToLdap(cmd.getDomainId(),cmd.getType(),cmd.getLdapDomain(),cmd.getAccountType());
+ }
+
+ private LinkDomainToLdapResponse linkDomainToLdap(Long domainId, String type, String name, short accountType) {
Validate.notNull(type, "type cannot be null. It should either be GROUP or OU");
Validate.notNull(domainId, "domainId cannot be null.");
Validate.notEmpty(name, "GROUP or OU name cannot be empty");
//Account type should be 0 or 2. check the constants in com.cloud.user.Account
Validate.isTrue(accountType==0 || accountType==2, "accountype should be either 0(normal user) or 2(domain admin)");
LinkType linkType = LdapManager.LinkType.valueOf(type.toUpperCase());
- LdapTrustMapVO vo = _ldapTrustMapDao.persist(new LdapTrustMapVO(domainId, linkType, name, accountType));
+ LdapTrustMapVO vo = _ldapTrustMapDao.persist(new LdapTrustMapVO(domainId, linkType, name, accountType, 0));
DomainVO domain = domainDao.findById(vo.getDomainId());
String domainUuid = "";
if (domain == null) {
@@ -290,4 +341,46 @@ public class LdapManagerImpl implements LdapManager, LdapValidator {
public LdapTrustMapVO getDomainLinkedToLdap(long domainId){
return _ldapTrustMapDao.findByDomainId(domainId);
}
+
+ @Override
+ public List getDomainLinkage(long domainId){
+ return _ldapTrustMapDao.searchByDomainId(domainId);
+ }
+
+ public LdapTrustMapVO getAccountLinkedToLdap(long domainId, long accountId){
+ return _ldapTrustMapDao.findByAccount(domainId, accountId);
+ }
+
+ @Override
+ public LdapTrustMapVO getLinkedLdapGroup(long domainId, String group) {
+ return _ldapTrustMapDao.findGroupInDomain(domainId, group);
+ }
+
+ @Override public LinkAccountToLdapResponse linkAccountToLdap(LinkAccountToLdapCmd cmd) {
+ Validate.notNull(_ldapConfiguration.getBaseDn(cmd.getDomainId()), "can not configure an ldap server and an ldap group/ou to a domain");
+ Validate.notNull(cmd.getDomainId(), "domainId cannot be null.");
+ Validate.notEmpty(cmd.getAccountName(), "accountName cannot be empty.");
+ Validate.notEmpty(cmd.getLdapDomain(), "ldapDomain cannot be empty, please supply a GROUP or OU name");
+ Validate.notNull(cmd.getType(), "type cannot be null. It should either be GROUP or OU");
+ Validate.notEmpty(cmd.getLdapDomain(), "GROUP or OU name cannot be empty");
+
+ LinkType linkType = LdapManager.LinkType.valueOf(cmd.getType().toUpperCase());
+ Account account = accountDao.findActiveAccount(cmd.getAccountName(),cmd.getDomainId());
+ if (account == null) {
+ account = new AccountVO(cmd.getAccountName(), cmd.getDomainId(), null, cmd.getAccountType(), UUID.randomUUID().toString());
+ accountDao.persist((AccountVO)account);
+ }
+ Long accountId = account.getAccountId();
+ LdapTrustMapVO vo = _ldapTrustMapDao.persist(new LdapTrustMapVO(cmd.getDomainId(), linkType, cmd.getLdapDomain(), cmd.getAccountType(), accountId));
+ DomainVO domain = domainDao.findById(vo.getDomainId());
+ String domainUuid = "";
+ if (domain == null) {
+ s_logger.error("no domain in database for id " + vo.getDomainId());
+ } else {
+ domainUuid = domain.getUuid();
+ }
+
+ LinkAccountToLdapResponse response = new LinkAccountToLdapResponse(domainUuid, vo.getType().toString(), vo.getName(), vo.getAccountType(), account.getUuid(), cmd.getAccountName());
+ return response;
+ }
}
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapTrustMapVO.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapTrustMapVO.java
index 8b1363816fa..c402747b813 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapTrustMapVO.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapTrustMapVO.java
@@ -45,6 +45,9 @@ public class LdapTrustMapVO implements InternalIdentity {
@Column(name = "domain_id")
private long domainId;
+ @Column(name = "account_id")
+ private long accountId;
+
@Column(name = "account_type")
private short accountType;
@@ -52,11 +55,12 @@ public class LdapTrustMapVO implements InternalIdentity {
public LdapTrustMapVO() {
}
- public LdapTrustMapVO(long domainId, LdapManager.LinkType type, String name, short accountType) {
+ public LdapTrustMapVO(long domainId, LdapManager.LinkType type, String name, short accountType, long accountId) {
this.domainId = domainId;
this.type = type;
this.name = name;
this.accountType = accountType;
+ this.accountId = accountId;
}
@Override
@@ -80,6 +84,10 @@ public class LdapTrustMapVO implements InternalIdentity {
return accountType;
}
+ public long getAccountId() {
+ return accountId;
+ }
+
@Override
public boolean equals(Object o) {
if (this == o) {
@@ -94,6 +102,9 @@ public class LdapTrustMapVO implements InternalIdentity {
if (domainId != that.domainId) {
return false;
}
+ if (accountId != that.accountId) {
+ return false;
+ }
if (accountType != that.accountType) {
return false;
}
@@ -109,6 +120,7 @@ public class LdapTrustMapVO implements InternalIdentity {
int result = type.hashCode();
result = 31 * result + name.hashCode();
result = 31 * result + (int) (domainId ^ (domainId >>> 32));
+ result = 31 * result + (int) (accountId ^ (accountId >>> 32));
result = 31 * result + (int) accountType;
return result;
}
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapUser.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapUser.java
index c4c334b5b6e..064ee412ab4 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapUser.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapUser.java
@@ -16,6 +16,9 @@
// under the License.
package org.apache.cloudstack.ldap;
+import java.util.ArrayList;
+import java.util.List;
+
public class LdapUser implements Comparable {
private final String email;
private final String principal;
@@ -24,8 +27,10 @@ public class LdapUser implements Comparable {
private final String username;
private final String domain;
private final boolean disabled;
+ private List memberships;
- public LdapUser(final String username, final String email, final String firstname, final String lastname, final String principal, String domain, boolean disabled) {
+ public LdapUser(final String username, final String email, final String firstname, final String lastname, final String principal, String domain, boolean disabled,
+ List memberships) {
this.username = username;
this.email = email;
this.firstname = firstname;
@@ -33,6 +38,7 @@ public class LdapUser implements Comparable {
this.principal = principal;
this.domain = domain;
this.disabled = disabled;
+ this.memberships = memberships == null ? new ArrayList<>() : memberships;
}
@Override
@@ -80,6 +86,9 @@ public class LdapUser implements Comparable {
return disabled;
}
+ public List getMemberships() {
+ return memberships;
+ }
@Override
public int hashCode() {
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapUserManager.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapUserManager.java
index 4e2bcf816b2..c9fcaa23cc0 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapUserManager.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapUserManager.java
@@ -30,17 +30,17 @@ public interface LdapUserManager {
MICROSOFTAD, OPENLDAP;
}
- public LdapUser getUser(final String username, final LdapContext context) throws NamingException, IOException;
+ public LdapUser getUser(final String username, final LdapContext context, Long domainId) throws NamingException, IOException;
- public LdapUser getUser(final String username, final String type, final String name, final LdapContext context) throws NamingException, IOException;
+ public LdapUser getUser(final String username, final String type, final String name, final LdapContext context, Long domainId) throws NamingException, IOException;
- public List getUsers(final LdapContext context) throws NamingException, IOException;
+ public List getUsers(final LdapContext context, Long domainId) throws NamingException, IOException;
- public List getUsers(final String username, final LdapContext context) throws NamingException, IOException;
+ public List getUsers(final String username, final LdapContext context, Long domainId) throws NamingException, IOException;
- public List getUsersInGroup(String groupName, LdapContext context) throws NamingException;
+ public List getUsersInGroup(String groupName, LdapContext context, Long domainId) throws NamingException;
- public List searchUsers(final LdapContext context) throws NamingException, IOException;
+ public List searchUsers(final LdapContext context, Long domainId) throws NamingException, IOException;
- public List searchUsers(final String username, final LdapContext context) throws NamingException, IOException;
+ public List searchUsers(final String username, final LdapContext context, Long domainId) throws NamingException, IOException;
}
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapUtils.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapUtils.java
index d54a6991def..da0859f77ca 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapUtils.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/LdapUtils.java
@@ -16,9 +16,12 @@
// under the License.
package org.apache.cloudstack.ldap;
+import javax.naming.NamingEnumeration;
import javax.naming.NamingException;
import javax.naming.directory.Attribute;
import javax.naming.directory.Attributes;
+import java.util.ArrayList;
+import java.util.List;
public final class LdapUtils {
public static String escapeLDAPSearchFilter(final String filter) {
@@ -56,6 +59,18 @@ public final class LdapUtils {
return null;
}
+ public static List getAttributeValues(final Attributes attributes, final String attributeName) throws NamingException {
+ ArrayList memberships = new ArrayList<>();
+ final Attribute attribute = attributes.get(attributeName);
+ if (attribute != null) {
+ NamingEnumeration> values = attribute.getAll();
+ while(values.hasMore()) {
+ memberships.add(String.valueOf(values.next()));
+ }
+ }
+ return memberships;
+ }
+
private LdapUtils() {
}
}
\ No newline at end of file
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/OpenLdapUserManagerImpl.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/OpenLdapUserManagerImpl.java
index 0c3e0d71705..cb3824a2ef0 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/OpenLdapUserManagerImpl.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/OpenLdapUserManagerImpl.java
@@ -50,41 +50,46 @@ public class OpenLdapUserManagerImpl implements LdapUserManager {
_ldapConfiguration = ldapConfiguration;
}
- protected LdapUser createUser(final SearchResult result) throws NamingException {
+ protected LdapUser createUser(final SearchResult result, Long domainId) throws NamingException {
final Attributes attributes = result.getAttributes();
- final String username = LdapUtils.getAttributeValue(attributes, _ldapConfiguration.getUsernameAttribute());
- final String email = LdapUtils.getAttributeValue(attributes, _ldapConfiguration.getEmailAttribute());
- final String firstname = LdapUtils.getAttributeValue(attributes, _ldapConfiguration.getFirstnameAttribute());
- final String lastname = LdapUtils.getAttributeValue(attributes, _ldapConfiguration.getLastnameAttribute());
+ final String username = LdapUtils.getAttributeValue(attributes, _ldapConfiguration.getUsernameAttribute(domainId));
+ final String email = LdapUtils.getAttributeValue(attributes, _ldapConfiguration.getEmailAttribute(domainId));
+ final String firstname = LdapUtils.getAttributeValue(attributes, _ldapConfiguration.getFirstnameAttribute(domainId));
+ final String lastname = LdapUtils.getAttributeValue(attributes, _ldapConfiguration.getLastnameAttribute(domainId));
final String principal = result.getNameInNamespace();
+ final List memberships = LdapUtils.getAttributeValues(attributes, _ldapConfiguration.getUserMemberOfAttribute(domainId));
String domain = principal.replace("cn=" + LdapUtils.getAttributeValue(attributes, _ldapConfiguration.getCommonNameAttribute()) + ",", "");
- domain = domain.replace("," + _ldapConfiguration.getBaseDn(), "");
+ domain = domain.replace("," + _ldapConfiguration.getBaseDn(domainId), "");
domain = domain.replace("ou=", "");
boolean disabled = isUserDisabled(result);
- return new LdapUser(username, email, firstname, lastname, principal, domain, disabled);
+ return new LdapUser(username, email, firstname, lastname, principal, domain, disabled, memberships);
}
- private String generateSearchFilter(final String username) {
+ private String generateSearchFilter(final String username, Long domainId) {
final StringBuilder userObjectFilter = new StringBuilder();
userObjectFilter.append("(objectClass=");
- userObjectFilter.append(_ldapConfiguration.getUserObject());
+ userObjectFilter.append(_ldapConfiguration.getUserObject(domainId));
userObjectFilter.append(")");
final StringBuilder usernameFilter = new StringBuilder();
usernameFilter.append("(");
- usernameFilter.append(_ldapConfiguration.getUsernameAttribute());
+ usernameFilter.append(_ldapConfiguration.getUsernameAttribute(domainId));
usernameFilter.append("=");
usernameFilter.append((username == null ? "*" : username));
usernameFilter.append(")");
final StringBuilder memberOfFilter = new StringBuilder();
- if (_ldapConfiguration.getSearchGroupPrinciple() != null) {
- memberOfFilter.append("(memberof=");
- memberOfFilter.append(_ldapConfiguration.getSearchGroupPrinciple());
+ if (_ldapConfiguration.getSearchGroupPrinciple(domainId) != null) {
+ if(s_logger.isDebugEnabled()) {
+ s_logger.debug("adding search filter for '" + _ldapConfiguration.getSearchGroupPrinciple(domainId) +
+ "', using " + _ldapConfiguration.getUserMemberOfAttribute(domainId));
+ }
+ memberOfFilter.append("(" + _ldapConfiguration.getUserMemberOfAttribute(domainId) + "=");
+ memberOfFilter.append(_ldapConfiguration.getSearchGroupPrinciple(domainId));
memberOfFilter.append(")");
}
@@ -98,10 +103,10 @@ public class OpenLdapUserManagerImpl implements LdapUserManager {
return result.toString();
}
- private String generateGroupSearchFilter(final String groupName) {
+ private String generateGroupSearchFilter(final String groupName, Long domainId) {
final StringBuilder groupObjectFilter = new StringBuilder();
groupObjectFilter.append("(objectClass=");
- groupObjectFilter.append(_ldapConfiguration.getGroupObject());
+ groupObjectFilter.append(_ldapConfiguration.getGroupObject(domainId));
groupObjectFilter.append(")");
final StringBuilder groupNameFilter = new StringBuilder();
@@ -121,8 +126,8 @@ public class OpenLdapUserManagerImpl implements LdapUserManager {
}
@Override
- public LdapUser getUser(final String username, final LdapContext context) throws NamingException, IOException {
- List result = searchUsers(username, context);
+ public LdapUser getUser(final String username, final LdapContext context, Long domainId) throws NamingException, IOException {
+ List result = searchUsers(username, context, domainId);
if (result!= null && result.size() == 1) {
return result.get(0);
} else {
@@ -131,29 +136,29 @@ public class OpenLdapUserManagerImpl implements LdapUserManager {
}
@Override
- public LdapUser getUser(final String username, final String type, final String name, final LdapContext context) throws NamingException, IOException {
+ public LdapUser getUser(final String username, final String type, final String name, final LdapContext context, Long domainId) throws NamingException, IOException {
String basedn;
if("OU".equals(type)) {
basedn = name;
} else {
- basedn = _ldapConfiguration.getBaseDn();
+ basedn = _ldapConfiguration.getBaseDn(domainId);
}
final StringBuilder userObjectFilter = new StringBuilder();
userObjectFilter.append("(objectClass=");
- userObjectFilter.append(_ldapConfiguration.getUserObject());
+ userObjectFilter.append(_ldapConfiguration.getUserObject(domainId));
userObjectFilter.append(")");
final StringBuilder usernameFilter = new StringBuilder();
usernameFilter.append("(");
- usernameFilter.append(_ldapConfiguration.getUsernameAttribute());
+ usernameFilter.append(_ldapConfiguration.getUsernameAttribute(domainId));
usernameFilter.append("=");
usernameFilter.append((username == null ? "*" : username));
usernameFilter.append(")");
final StringBuilder memberOfFilter = new StringBuilder();
if ("GROUP".equals(type)) {
- memberOfFilter.append("(").append(getMemberOfAttribute()).append("=");
+ memberOfFilter.append("(").append(getMemberOfAttribute(domainId)).append("=");
memberOfFilter.append(name);
memberOfFilter.append(")");
}
@@ -165,21 +170,21 @@ public class OpenLdapUserManagerImpl implements LdapUserManager {
searchQuery.append(memberOfFilter);
searchQuery.append(")");
- return searchUser(basedn, searchQuery.toString(), context);
+ return searchUser(basedn, searchQuery.toString(), context, domainId);
}
- protected String getMemberOfAttribute() {
- return "memberof";
+ protected String getMemberOfAttribute(final Long domainId) {
+ return _ldapConfiguration.getUserMemberOfAttribute(domainId);
}
@Override
- public List getUsers(final LdapContext context) throws NamingException, IOException {
- return getUsers(null, context);
+ public List getUsers(final LdapContext context, Long domainId) throws NamingException, IOException {
+ return getUsers(null, context, domainId);
}
@Override
- public List getUsers(final String username, final LdapContext context) throws NamingException, IOException {
- List users = searchUsers(username, context);
+ public List getUsers(final String username, final LdapContext context, Long domainId) throws NamingException, IOException {
+ List users = searchUsers(username, context, domainId);
if (CollectionUtils.isNotEmpty(users)) {
Collections.sort(users);
@@ -188,13 +193,13 @@ public class OpenLdapUserManagerImpl implements LdapUserManager {
}
@Override
- public List getUsersInGroup(String groupName, LdapContext context) throws NamingException {
- String attributeName = _ldapConfiguration.getGroupUniqueMemeberAttribute();
+ public List getUsersInGroup(String groupName, LdapContext context, Long domainId) throws NamingException {
+ String attributeName = _ldapConfiguration.getGroupUniqueMemberAttribute(domainId);
final SearchControls controls = new SearchControls();
controls.setSearchScope(_ldapConfiguration.getScope());
controls.setReturningAttributes(new String[] {attributeName});
- NamingEnumeration result = context.search(_ldapConfiguration.getBaseDn(), generateGroupSearchFilter(groupName), controls);
+ NamingEnumeration result = context.search(_ldapConfiguration.getBaseDn(domainId), generateGroupSearchFilter(groupName, domainId), controls);
final List users = new ArrayList();
//Expecting only one result which has all the users
@@ -205,7 +210,7 @@ public class OpenLdapUserManagerImpl implements LdapUserManager {
while (values.hasMoreElements()) {
String userdn = String.valueOf(values.nextElement());
try{
- users.add(getUserForDn(userdn, context));
+ users.add(getUserForDn(userdn, context, domainId));
} catch (NamingException e){
s_logger.info("Userdn: " + userdn + " Not Found:: Exception message: " + e.getMessage());
}
@@ -217,39 +222,42 @@ public class OpenLdapUserManagerImpl implements LdapUserManager {
return users;
}
- private LdapUser getUserForDn(String userdn, LdapContext context) throws NamingException {
+ private LdapUser getUserForDn(String userdn, LdapContext context, Long domainId) throws NamingException {
final SearchControls controls = new SearchControls();
controls.setSearchScope(_ldapConfiguration.getScope());
- controls.setReturningAttributes(_ldapConfiguration.getReturnAttributes());
+ controls.setReturningAttributes(_ldapConfiguration.getReturnAttributes(domainId));
- NamingEnumeration result = context.search(userdn, "(objectClass=" + _ldapConfiguration.getUserObject() + ")", controls);
+ NamingEnumeration result = context.search(userdn, "(objectClass=" + _ldapConfiguration.getUserObject(domainId) + ")", controls);
if (result.hasMoreElements()) {
- return createUser(result.nextElement());
+ return createUser(result.nextElement(), domainId);
} else {
throw new NamingException("No user found for dn " + userdn);
}
}
@Override
- public List searchUsers(final LdapContext context) throws NamingException, IOException {
- return searchUsers(null, context);
+ public List searchUsers(final LdapContext context, Long domainId) throws NamingException, IOException {
+ return searchUsers(null, context, domainId);
}
protected boolean isUserDisabled(SearchResult result) throws NamingException {
return false;
}
- public LdapUser searchUser(final String basedn, final String searchString, final LdapContext context) throws NamingException, IOException {
+ public LdapUser searchUser(final String basedn, final String searchString, final LdapContext context, Long domainId) throws NamingException, IOException {
final SearchControls searchControls = new SearchControls();
searchControls.setSearchScope(_ldapConfiguration.getScope());
- searchControls.setReturningAttributes(_ldapConfiguration.getReturnAttributes());
+ searchControls.setReturningAttributes(_ldapConfiguration.getReturnAttributes(domainId));
NamingEnumeration results = context.search(basedn, searchString, searchControls);
+ if(s_logger.isDebugEnabled()) {
+ s_logger.debug("searching user(s) with filter: \"" + searchString + "\"");
+ }
final List users = new ArrayList();
while (results.hasMoreElements()) {
final SearchResult result = results.nextElement();
- users.add(createUser(result));
+ users.add(createUser(result, domainId));
}
if (users.size() == 1) {
@@ -260,28 +268,28 @@ public class OpenLdapUserManagerImpl implements LdapUserManager {
}
@Override
- public List searchUsers(final String username, final LdapContext context) throws NamingException, IOException {
+ public List searchUsers(final String username, final LdapContext context, Long domainId) throws NamingException, IOException {
final SearchControls searchControls = new SearchControls();
searchControls.setSearchScope(_ldapConfiguration.getScope());
- searchControls.setReturningAttributes(_ldapConfiguration.getReturnAttributes());
+ searchControls.setReturningAttributes(_ldapConfiguration.getReturnAttributes(domainId));
- String basedn = _ldapConfiguration.getBaseDn();
+ String basedn = _ldapConfiguration.getBaseDn(domainId);
if (StringUtils.isBlank(basedn)) {
throw new IllegalArgumentException("ldap basedn is not configured");
}
byte[] cookie = null;
- int pageSize = _ldapConfiguration.getLdapPageSize();
+ int pageSize = _ldapConfiguration.getLdapPageSize(domainId);
context.setRequestControls(new Control[]{new PagedResultsControl(pageSize, Control.NONCRITICAL)});
final List users = new ArrayList();
NamingEnumeration results;
do {
- results = context.search(basedn, generateSearchFilter(username), searchControls);
+ results = context.search(basedn, generateSearchFilter(username, domainId), searchControls);
while (results.hasMoreElements()) {
final SearchResult result = results.nextElement();
if (!isUserDisabled(result)) {
- users.add(createUser(result));
+ users.add(createUser(result, domainId));
}
}
Control[] contextControls = context.getResponseControls();
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/dao/LdapConfigurationDao.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/dao/LdapConfigurationDao.java
index a2d5e65248e..e99c78be9b7 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/dao/LdapConfigurationDao.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/dao/LdapConfigurationDao.java
@@ -23,8 +23,19 @@ import org.apache.cloudstack.ldap.LdapConfigurationVO;
import com.cloud.utils.Pair;
import com.cloud.utils.db.GenericDao;
+/**
+ * TODO the domain value null now searches for that specifically and there is no way to search for all domains
+ */
public interface LdapConfigurationDao extends GenericDao {
+ /**
+ * @deprecated there might well be more then one ldap implementation on a host and or a double binding of several domains
+ * @param hostname
+ * @return
+ */
+ @Deprecated
LdapConfigurationVO findByHostname(String hostname);
- Pair, Integer> searchConfigurations(String hostname, int port);
+ LdapConfigurationVO find(String hostname, int port, Long domainId);
+
+ Pair, Integer> searchConfigurations(String hostname, int port, Long domainId);
}
\ No newline at end of file
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/dao/LdapConfigurationDaoImpl.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/dao/LdapConfigurationDaoImpl.java
index 8125f8cd2de..fa4c0af236f 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/dao/LdapConfigurationDaoImpl.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/dao/LdapConfigurationDaoImpl.java
@@ -32,7 +32,8 @@ import com.cloud.utils.db.SearchCriteria.Op;
@Component
public class LdapConfigurationDaoImpl extends GenericDaoBase implements LdapConfigurationDao {
private final SearchBuilder hostnameSearch;
- private final SearchBuilder listAllConfigurationsSearch;
+ private final SearchBuilder listGlobalConfigurationsSearch;
+ private final SearchBuilder listDomainConfigurationsSearch;
public LdapConfigurationDaoImpl() {
super();
@@ -40,10 +41,16 @@ public class LdapConfigurationDaoImpl extends GenericDaoBase, Integer> searchConfigurations(final String hostname, final int port) {
- final SearchCriteria sc = listAllConfigurationsSearch.create();
+ public LdapConfigurationVO find(String hostname, int port, Long domainId) {
+ SearchCriteria sc = getSearchCriteria(hostname, port, domainId);
+ return findOneBy(sc);
+ }
+
+ @Override
+ public Pair, Integer> searchConfigurations(final String hostname, final int port, final Long domainId) {
+ SearchCriteria sc = getSearchCriteria(hostname, port, domainId);
+ return searchAndCount(sc, null);
+ }
+
+ private SearchCriteria getSearchCriteria(String hostname, int port, Long domainId) {
+ SearchCriteria sc;
+ if (domainId == null) {
+ sc = listDomainConfigurationsSearch.create();
+ } else {
+ sc = listDomainConfigurationsSearch.create();
+ sc.setParameters("domain_id", domainId);
+ }
if (hostname != null) {
sc.setParameters("hostname", hostname);
}
- return searchAndCount(sc, null);
+ if (port > 0) {
+ sc.setParameters("port", port);
+ }
+ return sc;
}
}
\ No newline at end of file
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/dao/LdapTrustMapDao.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/dao/LdapTrustMapDao.java
index 7ef3799b3d8..c3d2f8aedf4 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/dao/LdapTrustMapDao.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/dao/LdapTrustMapDao.java
@@ -22,6 +22,11 @@ import org.apache.cloudstack.ldap.LdapTrustMapVO;
import com.cloud.utils.db.GenericDao;
+import java.util.List;
+
public interface LdapTrustMapDao extends GenericDao {
LdapTrustMapVO findByDomainId(long domainId);
+ LdapTrustMapVO findByAccount(long domainId, Long accountId);
+ LdapTrustMapVO findGroupInDomain(long domainId, String group);
+ List searchByDomainId(long domainId);
}
diff --git a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/dao/LdapTrustMapDaoImpl.java b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/dao/LdapTrustMapDaoImpl.java
index 57830982e70..0ecd3413d14 100644
--- a/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/dao/LdapTrustMapDaoImpl.java
+++ b/plugins/user-authenticators/ldap/src/org/apache/cloudstack/ldap/dao/LdapTrustMapDaoImpl.java
@@ -26,21 +26,55 @@ import org.springframework.stereotype.Component;
import com.cloud.utils.db.GenericDaoBase;
+import java.util.List;
+
@Component
public class LdapTrustMapDaoImpl extends GenericDaoBase implements LdapTrustMapDao {
private final SearchBuilder domainIdSearch;
+ private final SearchBuilder groupSearch;
public LdapTrustMapDaoImpl() {
super();
domainIdSearch = createSearchBuilder();
domainIdSearch.and("domainId", domainIdSearch.entity().getDomainId(), SearchCriteria.Op.EQ);
+ domainIdSearch.and("account_id", domainIdSearch.entity().getAccountId(),SearchCriteria.Op.EQ);
domainIdSearch.done();
+ groupSearch = createSearchBuilder();
+ groupSearch.and("domainId", groupSearch.entity().getDomainId(), SearchCriteria.Op.EQ);
+ groupSearch.and("name", groupSearch.entity().getName(),SearchCriteria.Op.EQ);
+ groupSearch.done();
}
@Override
public LdapTrustMapVO findByDomainId(long domainId) {
final SearchCriteria sc = domainIdSearch.create();
sc.setParameters("domainId", domainId);
+ sc.setParameters("account_id", 0);
return findOneBy(sc);
}
+
+ @Override
+ public LdapTrustMapVO findByAccount(long domainId, Long accountId) {
+ final SearchCriteria sc = domainIdSearch.create();
+ sc.setParameters("domainId", domainId);
+ sc.setParameters("account_id", accountId);
+ return findOneBy(sc);
+ }
+
+ @Override
+ public LdapTrustMapVO findGroupInDomain(long domainId, String group){
+ final SearchCriteria sc = groupSearch.create();
+ sc.setParameters("domainId", domainId);
+ sc.setParameters("name", group);
+ return findOneBy(sc);
+
+ }
+
+ @Override
+ public List searchByDomainId(long domainId) {
+ final SearchCriteria sc = domainIdSearch.create();
+ sc.setParameters("domainId", domainId);
+ return search(sc,null);
+ }
+
}
diff --git a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/ADLdapUserManagerImplSpec.groovy b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/ADLdapUserManagerImplSpec.groovy
index 93b1b17a460..4b631b44e3b 100644
--- a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/ADLdapUserManagerImplSpec.groovy
+++ b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/ADLdapUserManagerImplSpec.groovy
@@ -69,13 +69,13 @@ class ADLdapUserManagerImplSpec extends spock.lang.Specification {
def "test getUsersInGroup null group"() {
ldapConfiguration.getScope() >> SearchControls.SUBTREE_SCOPE
- ldapConfiguration.getReturnAttributes() >> ["username", "firstname", "lastname", "email"]
- ldapConfiguration.getBaseDn() >>> [null, null, "DC=cloud,DC=citrix,DC=com"]
+ ldapConfiguration.getReturnAttributes(null) >> ["username", "firstname", "lastname", "email"]
+ ldapConfiguration.getBaseDn(null) >>> [null, null, "DC=cloud,DC=citrix,DC=com"]
LdapContext context = Mock(LdapContext);
when:
- def result = adLdapUserManager.getUsersInGroup(group, context)
+ def result = adLdapUserManager.getUsersInGroup(group, context,null)
then:
thrown(IllegalArgumentException)
where:
diff --git a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapAuthenticatorSpec.groovy b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapAuthenticatorSpec.groovy
index ca19e8c633b..1ff5fce4243 100644
--- a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapAuthenticatorSpec.groovy
+++ b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapAuthenticatorSpec.groovy
@@ -49,8 +49,8 @@ class LdapAuthenticatorSpec extends spock.lang.Specification {
def ldapUser = Mock(LdapUser)
ldapUser.isDisabled() >> false
ldapManager.isLdapEnabled() >> true
- ldapManager.getUser("rmurphy") >> ldapUser
- ldapManager.canAuthenticate(_, _) >> false
+ ldapManager.getUser("rmurphy", null) >> ldapUser
+ ldapManager.canAuthenticate(_, _, _) >> false
UserAccountDao userAccountDao = Mock(UserAccountDao)
userAccountDao.getUserAccount(_, _) >> new UserAccountVO()
@@ -84,8 +84,8 @@ class LdapAuthenticatorSpec extends spock.lang.Specification {
def ldapUser = Mock(LdapUser)
ldapUser.isDisabled() >> false
ldapManager.isLdapEnabled() >> true
- ldapManager.canAuthenticate(_, _) >> true
- ldapManager.getUser("rmurphy") >> ldapUser
+ ldapManager.canAuthenticate(_, _, _) >> true
+ ldapManager.getUser("rmurphy", null) >> ldapUser
UserAccountDao userAccountDao = Mock(UserAccountDao)
userAccountDao.getUserAccount(_, _) >> new UserAccountVO()
@@ -144,7 +144,7 @@ class LdapAuthenticatorSpec extends spock.lang.Specification {
userAccountDao.getUserAccount(username, domainId) >> userAccount
userAccount.getId() >> 1
ldapManager.getDomainLinkedToLdap(domainId) >> new LdapTrustMapVO(domainId, type, name, (short)2)
- ldapManager.getUser(username, type.toString(), name) >> new LdapUser(username, "email", "firstname", "lastname", "principal", "domain", true)
+ ldapManager.getUser(username, type.toString(), name) >> new LdapUser(username, "email", "firstname", "lastname", "principal", "domain", true, null)
//user should be disabled in cloudstack
accountManager.disableUser(1) >> userAccount
@@ -173,8 +173,8 @@ class LdapAuthenticatorSpec extends spock.lang.Specification {
ldapManager.isLdapEnabled() >> true
userAccountDao.getUserAccount(username, domainId) >> null
ldapManager.getDomainLinkedToLdap(domainId) >> new LdapTrustMapVO(domainId, type, name, (short)0)
- ldapManager.getUser(username, type.toString(), name) >> new LdapUser(username, "email", "firstname", "lastname", "principal", "domain", false)
- ldapManager.canAuthenticate(_,_) >> true
+ ldapManager.getUser(username, type.toString(), name) >> new LdapUser(username, "email", "firstname", "lastname", "principal", "domain", false, null)
+ ldapManager.canAuthenticate(_, _, _) >> true
//user should be created in cloudstack
accountManager.createUserAccount(username, "", "firstname", "lastname", "email", null, username, (short) 2, domainId, username, null, _, _, User.Source.LDAP) >> Mock(UserAccount)
@@ -206,8 +206,8 @@ class LdapAuthenticatorSpec extends spock.lang.Specification {
userAccount.getId() >> 1
userAccount.getState() >> Account.State.disabled.toString()
ldapManager.getDomainLinkedToLdap(domainId) >> new LdapTrustMapVO(domainId, type, name, (short)2)
- ldapManager.getUser(username, type.toString(), name) >> new LdapUser(username, "email", "firstname", "lastname", "principal", "domain", false)
- ldapManager.canAuthenticate(_,_) >> true
+ ldapManager.getUser(username, type.toString(), name) >> new LdapUser(username, "email", "firstname", "lastname", "principal", "domain", false, null)
+ ldapManager.canAuthenticate(_, _, _) >> true
//user should be enabled in cloudstack if disabled
accountManager.enableUser(1) >> userAccount
@@ -237,8 +237,8 @@ class LdapAuthenticatorSpec extends spock.lang.Specification {
UserAccount userAccount = Mock(UserAccount)
userAccountDao.getUserAccount(username, domainId) >> userAccount
ldapManager.getDomainLinkedToLdap(domainId) >> new LdapTrustMapVO(domainId, type, name, (short)2)
- ldapManager.getUser(username, type.toString(), name) >> new LdapUser(username, "email", "firstname", "lastname", "principal", "domain", false)
- ldapManager.canAuthenticate(_,_) >> false
+ ldapManager.getUser(username, type.toString(), name) >> new LdapUser(username, "email", "firstname", "lastname", "principal", "domain", false, null)
+ ldapManager.canAuthenticate(_, _, _) >> false
when:
Pair result = ldapAuthenticator.authenticate(username, "password", domainId, null)
diff --git a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapConfigurationDaoImplSpec.groovy b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapConfigurationDaoImplSpec.groovy
index 144890957f2..e94b0d40fb4 100644
--- a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapConfigurationDaoImplSpec.groovy
+++ b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapConfigurationDaoImplSpec.groovy
@@ -22,8 +22,8 @@ class LdapConfigurationDaoImplSpec extends spock.lang.Specification {
def "Test setting up of a LdapConfigurationDao"() {
given: "We have an LdapConfigurationDao implementation"
def ldapConfigurationDaoImpl = new LdapConfigurationDaoImpl();
- expect: "that hostnameSearch and listAllConfigurationsSearch is configured"
+ expect: "that hostnameSearch and listDomainConfigurationsSearch is configured"
ldapConfigurationDaoImpl.hostnameSearch != null;
- ldapConfigurationDaoImpl.listAllConfigurationsSearch != null
+ ldapConfigurationDaoImpl.listDomainConfigurationsSearch != null
}
}
diff --git a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapConfigurationSpec.groovy b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapConfigurationSpec.groovy
index 6f967cc6d8b..ec84d38e125 100644
--- a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapConfigurationSpec.groovy
+++ b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapConfigurationSpec.groovy
@@ -19,55 +19,26 @@ package groovy.org.apache.cloudstack.ldap
import org.apache.cloudstack.framework.config.ConfigKey
import org.apache.cloudstack.framework.config.dao.ConfigurationDao;
import com.cloud.utils.Pair
-import org.apache.cloudstack.api.ServerApiException
import org.apache.cloudstack.framework.config.impl.ConfigDepotImpl
import org.apache.cloudstack.framework.config.impl.ConfigurationVO
import org.apache.cloudstack.ldap.LdapConfiguration
import org.apache.cloudstack.ldap.LdapConfigurationVO
-import org.apache.cloudstack.ldap.LdapManager
import org.apache.cloudstack.ldap.LdapUserManager
import org.apache.cloudstack.ldap.dao.LdapConfigurationDao
-import org.apache.cxf.common.util.StringUtils
import javax.naming.directory.SearchControls
class LdapConfigurationSpec extends spock.lang.Specification {
def "Test that getAuthentication returns none"() {
given: "We have a ConfigDao, LdapManager and LdapConfiguration"
- def configDao = Mock(ConfigurationDao)
def ldapConfigurationDao = Mock(LdapConfigurationDao)
- def ldapConfiguration = new LdapConfiguration(configDao, ldapConfigurationDao)
+ def ldapConfiguration = new LdapConfiguration(ldapConfigurationDao)
when: "Get authentication is called"
String authentication = ldapConfiguration.getAuthentication()
then: "none should be returned"
authentication == "none"
}
- def "Test that getAuthentication returns simple"() {
- given: "We have a configDao, LdapManager and LdapConfiguration with bind principle and password set"
- def configDao = Mock(ConfigurationDao)
- def ldapConfigurationDao = Mock(LdapConfigurationDao)
- def ldapConfiguration = new LdapConfiguration(configDao, ldapConfigurationDao)
- configDao.getValue("ldap.bind.password") >> "password"
- configDao.getValue("ldap.bind.principal") >> "cn=rmurphy,dc=cloudstack,dc=org"
- when: "Get authentication is called"
- String authentication = ldapConfiguration.getAuthentication()
- then: "authentication should be set to simple"
- authentication == "simple"
- }
-
- def "Test that getBaseDn returns dc=cloudstack,dc=org"() {
- given: "We have a ConfigDao, LdapManager and ldapConfiguration with a baseDn value set."
- def configDao = Mock(ConfigurationDao)
- configDao.getValue("ldap.basedn") >> "dc=cloudstack,dc=org"
- def ldapConfigurationDao = Mock(LdapConfigurationDao)
- def ldapConfiguration = new LdapConfiguration(configDao, ldapConfigurationDao)
- when: "Get basedn is called"
- String baseDn = ldapConfiguration.getBaseDn();
- then: "The set baseDn should be returned"
- baseDn == "dc=cloudstack,dc=org"
- }
-
def "Test that getEmailAttribute returns mail"() {
given: "Given that we have a ConfigDao, LdapManager and LdapConfiguration"
def configDao = Mock(ConfigurationDao)
@@ -178,87 +149,12 @@ class LdapConfigurationSpec extends spock.lang.Specification {
LdapConfiguration ldapConfiguration = new LdapConfiguration(configDao, ldapConfigurationDao)
when: "A request is made to get the providerUrl"
- String providerUrl = ldapConfiguration.getProviderUrl()
+ String providerUrl = ldapConfiguration.getProviderUrl(_)
then: "The providerUrl should be given."
providerUrl == "ldap://localhost:389"
}
- def "Test that get search group principle returns successfully"() {
- given: "We have a ConfigDao with a value for ldap.search.group.principle and an LdapConfiguration"
- def configDao = Mock(ConfigurationDao)
- configDao.getValue("ldap.search.group.principle") >> "cn=cloudstack,cn=users,dc=cloudstack,dc=org"
- def ldapConfigurationDao = Mock(LdapConfigurationDao)
- LdapConfiguration ldapConfiguration = new LdapConfiguration(configDao, ldapConfigurationDao)
-
- when: "A request is made to get the search group principle"
- String result = ldapConfiguration.getSearchGroupPrinciple();
-
- then: "The result holds the same value configDao did"
- result == "cn=cloudstack,cn=users,dc=cloudstack,dc=org"
- }
-
- def "Test that getTrustStorePassword resopnds"() {
- given: "We have a ConfigDao with a value for truststore password"
- def configDao = Mock(ConfigurationDao)
- configDao.getValue("ldap.truststore.password") >> "password"
- def ldapConfigurationDao = Mock(LdapConfigurationDao)
- LdapConfiguration ldapConfiguration = new LdapConfiguration(configDao, ldapConfigurationDao)
-
- when: "A request is made to get the truststore password"
- String result = ldapConfiguration.getTrustStorePassword()
-
- then: "The result is password"
- result == "password";
- }
-
- def "Test that getSSLStatus can be true"() {
- given: "We have a ConfigDao with values for truststore and truststore password set"
- def configDao = Mock(ConfigurationDao)
- configDao.getValue("ldap.truststore") >> "/tmp/ldap.ts"
- configDao.getValue("ldap.truststore.password") >> "password"
- def ldapConfigurationDao = Mock(LdapConfigurationDao)
- LdapConfiguration ldapConfiguration = new LdapConfiguration(configDao, ldapConfigurationDao)
-
- when: "A request is made to get the status of SSL"
- boolean result = ldapConfiguration.getSSLStatus();
-
- then: "The response should be true"
- result == true
- }
-
- def "Test getgroupobject"() {
- given: "We have configdao for ldap group object"
- def configDao = Mock(ConfigurationDao)
- configDao.getValue("ldap.group.object") >> groupObject
-
- def ldapConfigurationDao = Mock(LdapConfigurationDao)
- LdapConfiguration ldapConfiguration = new LdapConfiguration(configDao, ldapConfigurationDao)
- def expectedResult = groupObject == null ? "groupOfUniqueNames" : groupObject
-
- def result = ldapConfiguration.getGroupObject()
- expect:
- result == expectedResult
- where:
- groupObject << [null, "", "groupOfUniqueNames"]
- }
-
- def "Test getGroupUniqueMemeberAttribute"() {
- given: "We have configdao for ldap group object"
- def configDao = Mock(ConfigurationDao)
- configDao.getValue("ldap.group.user.uniquemember") >> groupObject
-
- def ldapConfigurationDao = Mock(LdapConfigurationDao)
- LdapConfiguration ldapConfiguration = new LdapConfiguration(configDao, ldapConfigurationDao)
- def expectedResult = groupObject == null ? "uniquemember" : groupObject
-
- def result = ldapConfiguration.getGroupUniqueMemeberAttribute()
- expect:
- result == expectedResult
- where:
- groupObject << [null, "", "uniquemember"]
- }
-
def "Test getReadTimeout"() {
given: "We have configdao for ldap group object"
def configDao = Mock(ConfigurationDao)
@@ -275,7 +171,7 @@ class LdapConfigurationSpec extends spock.lang.Specification {
def expected = timeout == null ? 1000 : timeout.toLong() //1000 is the default value
- def result = ldapConfiguration.getReadTimeout()
+ def result = ldapConfiguration.getReadTimeout(null)
expect:
result == expected
where:
@@ -298,7 +194,7 @@ class LdapConfigurationSpec extends spock.lang.Specification {
def expected = provider.equalsIgnoreCase("microsoftad") ? LdapUserManager.Provider.MICROSOFTAD : LdapUserManager.Provider.OPENLDAP //"openldap" is the default value
- def result = ldapConfiguration.getLdapProvider()
+ def result = ldapConfiguration.getLdapProvider(null)
expect:
println "asserting for provider configuration: " + provider
result == expected
diff --git a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapContextFactorySpec.groovy b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapContextFactorySpec.groovy
index 15408833a65..eead0bcd28c 100644
--- a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapContextFactorySpec.groovy
+++ b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapContextFactorySpec.groovy
@@ -22,7 +22,6 @@ import spock.lang.Shared
import javax.naming.NamingException
import javax.naming.directory.SearchControls
-import javax.naming.ldap.LdapContext
class LdapContextFactorySpec extends spock.lang.Specification {
@Shared
@@ -41,7 +40,7 @@ class LdapContextFactorySpec extends spock.lang.Specification {
ldapConfiguration = Mock(LdapConfiguration)
ldapConfiguration.getFactory() >> "com.sun.jndi.ldap.LdapCtxFactory"
- ldapConfiguration.getProviderUrl() >> "ldap://localhost:389"
+ ldapConfiguration.getProviderUrl(_) >> "ldap://localhost:389"
ldapConfiguration.getAuthentication() >> "none"
ldapConfiguration.getScope() >> SearchControls.SUBTREE_SCOPE
ldapConfiguration.getReturnAttributes() >> ["uid", "mail", "cn"]
@@ -49,11 +48,11 @@ class LdapContextFactorySpec extends spock.lang.Specification {
ldapConfiguration.getEmailAttribute() >> "mail"
ldapConfiguration.getFirstnameAttribute() >> "givenname"
ldapConfiguration.getLastnameAttribute() >> "sn"
- ldapConfiguration.getBaseDn() >> "dc=cloudstack,dc=org"
+ ldapConfiguration.getBaseDn(_) >> "dc=cloudstack,dc=org"
ldapConfiguration.getSSLStatus() >> true
ldapConfiguration.getTrustStore() >> "/tmp/ldap.ts"
ldapConfiguration.getTrustStorePassword() >> "password"
- ldapConfiguration.getReadTimeout() >> 1000
+ ldapConfiguration.getReadTimeout(_) >> 1000
ldapConfiguration.getLdapPageSize() >> 1
username = "rmurphy"
@@ -87,7 +86,7 @@ class LdapContextFactorySpec extends spock.lang.Specification {
def result = ldapContextFactory.getEnvironment(null, null, null, true)
then: "The resulting values should be set"
- result['java.naming.provider.url'] == ldapConfiguration.getProviderUrl()
+ result['java.naming.provider.url'] == ldapConfiguration.getProviderUrl(null)
result['java.naming.factory.initial'] == ldapConfiguration.getFactory()
result['java.naming.security.principal'] == null
result['java.naming.security.authentication'] == ldapConfiguration.getAuthentication()
@@ -102,7 +101,7 @@ class LdapContextFactorySpec extends spock.lang.Specification {
def result = ldapContextFactory.getEnvironment(principal, password, null, false)
then: "The resulting values should be set"
- result['java.naming.provider.url'] == ldapConfiguration.getProviderUrl()
+ result['java.naming.provider.url'] == ldapConfiguration.getProviderUrl(null)
result['java.naming.factory.initial'] == ldapConfiguration.getFactory()
result['java.naming.security.principal'] == principal
result['java.naming.security.authentication'] == "simple"
diff --git a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapCreateAccountCmdSpec.groovy b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapCreateAccountCmdSpec.groovy
index a0b20bbcb13..db4fa232b50 100644
--- a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapCreateAccountCmdSpec.groovy
+++ b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapCreateAccountCmdSpec.groovy
@@ -16,54 +16,13 @@
// under the License.
package groovy.org.apache.cloudstack.ldap
-import com.cloud.exception.InvalidParameterValueException
-import org.apache.cloudstack.api.ServerApiException
-import org.apache.cloudstack.api.command.LdapAddConfigurationCmd
-import org.apache.cloudstack.api.response.LdapConfigurationResponse
-
import org.apache.cloudstack.ldap.LdapUser;
import org.apache.cloudstack.ldap.LdapManager;
-import org.apache.cloudstack.api.command.LdapCreateAccountCmd;
-import org.apache.cloudstack.context.CallContext;
-
-import com.cloud.user.AccountService;
-import com.cloud.user.UserAccount;
-import com.cloud.user.UserAccountVO
-import org.apache.cloudstack.ldap.NoLdapUserMatchingQueryException;
-
-import javax.naming.NamingException
+import org.apache.cloudstack.api.command.LdapCreateAccountCmd
+import com.cloud.user.AccountService
class LdapCreateAccountCmdSpec extends spock.lang.Specification {
-
- def "Test failure to retrive LDAP user"() {
- given: "We have an LdapManager, AccountService and LdapCreateAccountCmd and LDAP user that doesn't exist"
- LdapManager ldapManager = Mock(LdapManager)
- ldapManager.getUser(_) >> { throw new NoLdapUserMatchingQueryException() }
- AccountService accountService = Mock(AccountService)
- def ldapCreateAccountCmd = Spy(LdapCreateAccountCmd, constructorArgs: [ldapManager, accountService])
- ldapCreateAccountCmd.getCurrentContext() >> Mock(CallContext)
- CallContext context = ldapCreateAccountCmd.getCurrentContext()
- when: "An an account is created"
- ldapCreateAccountCmd.execute()
- then: "It fails and an exception is thrown"
- thrown ServerApiException
- }
-
- def "Test failed creation due to a null response from cloudstack account creater"() {
- given: "We have an LdapManager, AccountService and LdapCreateAccountCmd"
- LdapManager ldapManager = Mock(LdapManager)
- ldapManager.getUser(_) >> new LdapUser("rmurphy", "rmurphy@cloudstack.org", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false)
- AccountService accountService = Mock(AccountService)
- def ldapCreateAccountCmd = Spy(LdapCreateAccountCmd, constructorArgs: [ldapManager, accountService])
- ldapCreateAccountCmd.getCurrentContext() >> Mock(CallContext)
- ldapCreateAccountCmd.createCloudstackUserAccount(_, _, _) >> null
- when: "Cloudstack fail to create the user"
- ldapCreateAccountCmd.execute()
- then: "An exception is thrown"
- thrown ServerApiException
- }
-
def "Test command name"() {
given: "We have an LdapManager, AccountService and LdapCreateAccountCmd"
LdapManager ldapManager = Mock(LdapManager)
@@ -105,7 +64,7 @@ class LdapCreateAccountCmdSpec extends spock.lang.Specification {
AccountService accountService = Mock(AccountService)
def ldapCreateAccountCmd = new LdapCreateAccountCmd(ldapManager, accountService);
when: "a user with an username, email, firstname and lastname is validated"
- def result = ldapCreateAccountCmd.validateUser(new LdapUser("username", "email", "firstname", "lastname", "principal", "domain", false))
+ def result = ldapCreateAccountCmd.validateUser(new LdapUser("username", "email", "firstname", "lastname", "principal", "domain", false, null))
then: "the result is true"
result == true
}
@@ -116,7 +75,7 @@ class LdapCreateAccountCmdSpec extends spock.lang.Specification {
AccountService accountService = Mock(AccountService)
def ldapCreateAccountCmd = new LdapCreateAccountCmd(ldapManager, accountService)
when: "A user with no email address attempts to validate"
- ldapCreateAccountCmd.validateUser(new LdapUser("username", null, "firstname", "lastname", "principal", "domain", false))
+ ldapCreateAccountCmd.validateUser(new LdapUser("username", null, "firstname", "lastname", "principal", "domain", false, null))
then: "An exception is thrown"
thrown Exception
}
@@ -138,7 +97,7 @@ class LdapCreateAccountCmdSpec extends spock.lang.Specification {
AccountService accountService = Mock(AccountService)
def ldapCreateAccountCmd = new LdapCreateAccountCmd(ldapManager, accountService)
when: "A user with no lastname attempts to validate"
- ldapCreateAccountCmd.validateUser(new LdapUser("username", "email", "firstname", null, "principal", "domain", false))
+ ldapCreateAccountCmd.validateUser(new LdapUser("username", "email", "firstname", null, "principal", "domain", false, null))
then: "An exception is thown"
thrown Exception
}
diff --git a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapDeleteConfigurationCmdSpec.groovy b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapDeleteConfigurationCmdSpec.groovy
index 31d56ef68cb..caa524701b2 100644
--- a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapDeleteConfigurationCmdSpec.groovy
+++ b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapDeleteConfigurationCmdSpec.groovy
@@ -27,7 +27,7 @@ class LdapDeleteConfigurationCmdSpec extends spock.lang.Specification {
def "Test failed response from execute"() {
given: "We have an LdapManager and LdapDeleteConfigurationCmd"
def ldapManager = Mock(LdapManager)
- ldapManager.deleteConfiguration(_) >> { throw new InvalidParameterValueException() }
+ ldapManager.deleteConfiguration(_, 0, null) >> { throw new InvalidParameterValueException() }
def ldapDeleteConfigurationCmd = new LdapDeleteConfigurationCmd(ldapManager)
when:"LdapDeleteConfigurationCmd is executed and no configuration exists"
ldapDeleteConfigurationCmd.execute()
@@ -48,7 +48,7 @@ class LdapDeleteConfigurationCmdSpec extends spock.lang.Specification {
def "Test successful response from execute"() {
given: "We have an LdapManager and LdapDeleteConfigurationCmd"
def ldapManager = Mock(LdapManager)
- ldapManager.deleteConfiguration(_) >> new LdapConfigurationResponse("localhost")
+ ldapManager.deleteConfiguration(_, 0, null) >> new LdapConfigurationResponse("localhost")
def ldapDeleteConfigurationCmd = new LdapDeleteConfigurationCmd(ldapManager)
when: "LdapDeleteConfigurationCmd is executed"
ldapDeleteConfigurationCmd.execute()
diff --git a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapImportUsersCmdSpec.groovy b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapImportUsersCmdSpec.groovy
index 434151ae234..68b910811c7 100644
--- a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapImportUsersCmdSpec.groovy
+++ b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapImportUsersCmdSpec.groovy
@@ -24,10 +24,8 @@ import com.cloud.user.DomainService
import com.cloud.user.User
import com.cloud.user.UserAccountVO
import com.cloud.user.UserVO
-import org.apache.cloudstack.api.command.LdapCreateAccountCmd
import org.apache.cloudstack.api.command.LdapImportUsersCmd
import org.apache.cloudstack.api.response.LdapUserResponse
-import org.apache.cloudstack.context.CallContext
import org.apache.cloudstack.ldap.LdapManager
import org.apache.cloudstack.ldap.LdapUser
@@ -53,9 +51,9 @@ class LdapImportUsersCmdSpec extends spock.lang.Specification {
def accountService = Mock(AccountService)
List users = new ArrayList()
- users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false))
- users.add(new LdapUser("bob", "bob@test.com", "Robert", "Young", "cn=bob,ou=engineering,dc=cloudstack,dc=org", "engineering", false))
- ldapManager.getUsers() >> users
+ users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false, null))
+ users.add(new LdapUser("bob", "bob@test.com", "Robert", "Young", "cn=bob,ou=engineering,dc=cloudstack,dc=org", "engineering", false, null))
+ ldapManager.getUsers(null) >> users
LdapUserResponse response1 = new LdapUserResponse("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering")
LdapUserResponse response2 = new LdapUserResponse("bob", "bob@test.com", "Robert", "Young", "cn=bob,ou=engineering,dc=cloudstack,dc=org", "engineering")
ldapManager.createLdapUserResponse(_) >>> [response1, response2]
@@ -81,9 +79,9 @@ class LdapImportUsersCmdSpec extends spock.lang.Specification {
def accountService = Mock(AccountService)
List users = new ArrayList()
- users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false))
- users.add(new LdapUser("bob", "bob@test.com", "Robert", "Young", "cn=bob,ou=engineering,dc=cloudstack,dc=org", "engineering", false))
- ldapManager.getUsersInGroup("TestGroup") >> users
+ users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false, null))
+ users.add(new LdapUser("bob", "bob@test.com", "Robert", "Young", "cn=bob,ou=engineering,dc=cloudstack,dc=org", "engineering", false, null))
+ ldapManager.getUsersInGroup("TestGroup", null) >> users
LdapUserResponse response1 = new LdapUserResponse("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering")
LdapUserResponse response2 = new LdapUserResponse("bob", "bob@test.com", "Robert", "Young", "cn=bob,ou=engineering,dc=cloudstack,dc=org", "engineering")
ldapManager.createLdapUserResponse(_) >>> [response1, response2]
@@ -110,9 +108,9 @@ class LdapImportUsersCmdSpec extends spock.lang.Specification {
def accountService = Mock(AccountService)
List users = new ArrayList()
- users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false))
- users.add(new LdapUser("bob", "bob@test.com", "Robert", "Young", "cn=bob,ou=engineering,dc=cloudstack,dc=org", "engineering", false))
- ldapManager.getUsersInGroup("TestGroup") >> users
+ users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false, null))
+ users.add(new LdapUser("bob", "bob@test.com", "Robert", "Young", "cn=bob,ou=engineering,dc=cloudstack,dc=org", "engineering", false, null))
+ ldapManager.getUsersInGroup("TestGroup", null) >> users
LdapUserResponse response1 = new LdapUserResponse("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering")
LdapUserResponse response2 = new LdapUserResponse("bob", "bob@test.com", "Robert", "Young", "cn=bob,ou=engineering,dc=cloudstack,dc=org", "engineering")
ldapManager.createLdapUserResponse(_) >>> [response1, response2]
@@ -139,9 +137,9 @@ class LdapImportUsersCmdSpec extends spock.lang.Specification {
def accountService = Mock(AccountService)
List users = new ArrayList()
- users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false))
- users.add(new LdapUser("bob", "bob@test.com", "Robert", "Young", "cn=bob,ou=engineering,dc=cloudstack,dc=org", "engineering", false))
- ldapManager.getUsers() >> users
+ users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false, null))
+ users.add(new LdapUser("bob", "bob@test.com", "Robert", "Young", "cn=bob,ou=engineering,dc=cloudstack,dc=org", "engineering", false, null))
+ ldapManager.getUsers(null) >> users
LdapUserResponse response1 = new LdapUserResponse("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering")
LdapUserResponse response2 = new LdapUserResponse("bob", "bob@test.com", "Robert", "Young", "cn=bob,ou=engineering,dc=cloudstack,dc=org", "engineering")
ldapManager.createLdapUserResponse(_) >>> [response1, response2]
@@ -169,8 +167,8 @@ class LdapImportUsersCmdSpec extends spock.lang.Specification {
ldapImportUsersCmd.domainId = varDomainId
ldapImportUsersCmd.groupName = varGroupName
- def ldapUser1 = new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false)
- def ldapUser2 = new LdapUser("bob", "bob@test.com", "Robert", "Young", "cn=bob,ou=engineering,dc=cloudstack,dc=org", "engineering", false);
+ def ldapUser1 = new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false, null)
+ def ldapUser2 = new LdapUser("bob", "bob@test.com", "Robert", "Young", "cn=bob,ou=engineering,dc=cloudstack,dc=org", "engineering", false, null);
Domain domain = new DomainVO(expectedDomainName, 1L, 1L, expectedDomainName, UUID.randomUUID().toString());
if (varDomainId != null) {
@@ -204,8 +202,8 @@ class LdapImportUsersCmdSpec extends spock.lang.Specification {
given: "We have an LdapManager, DomainService, two users and a LdapImportUsersCmd"
def ldapManager = Mock(LdapManager)
List users = new ArrayList()
- users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false))
- ldapManager.getUsers() >> users
+ users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false, null))
+ ldapManager.getUsers(null) >> users
LdapUserResponse response1 = new LdapUserResponse("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering")
ldapManager.createLdapUserResponse(_) >>> response1
@@ -234,8 +232,8 @@ class LdapImportUsersCmdSpec extends spock.lang.Specification {
given: "We have an LdapManager, DomainService, two users and a LdapImportUsersCmd"
def ldapManager = Mock(LdapManager)
List users = new ArrayList()
- users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false))
- ldapManager.getUsers() >> users
+ users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false, null))
+ ldapManager.getUsers(null) >> users
LdapUserResponse response1 = new LdapUserResponse("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering")
ldapManager.createLdapUserResponse(_) >>> response1
@@ -263,8 +261,8 @@ class LdapImportUsersCmdSpec extends spock.lang.Specification {
given: "We have an LdapManager, DomainService, two users and a LdapImportUsersCmd"
def ldapManager = Mock(LdapManager)
List users = new ArrayList()
- users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false))
- ldapManager.getUsers() >> users
+ users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false, null))
+ ldapManager.getUsers(null) >> users
LdapUserResponse response1 = new LdapUserResponse("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering")
ldapManager.createLdapUserResponse(_) >>> response1
diff --git a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapListUsersCmdSpec.groovy b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapListUsersCmdSpec.groovy
index 5247a1ec895..d6410d96866 100644
--- a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapListUsersCmdSpec.groovy
+++ b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapListUsersCmdSpec.groovy
@@ -40,7 +40,7 @@ class LdapListUsersCmdSpec extends spock.lang.Specification {
def "Test successful empty response from execute"() {
given: "We have a LdapManager with no users, QueryService and a LdapListUsersCmd"
def ldapManager = Mock(LdapManager)
- ldapManager.getUsers() >> {throw new NoLdapUserMatchingQueryException()}
+ ldapManager.getUsers(null) >> {throw new NoLdapUserMatchingQueryException()}
def queryService = Mock(QueryService)
def ldapListUsersCmd = new LdapListUsersCmd(ldapManager, queryService)
when: "LdapListUsersCmd is executed"
@@ -53,8 +53,8 @@ class LdapListUsersCmdSpec extends spock.lang.Specification {
given: "We have an LdapManager, one user, QueryService and a LdapListUsersCmd"
def ldapManager = Mock(LdapManager)
List users = new ArrayList()
- users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", null, false))
- ldapManager.getUsers() >> users
+ users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", null, false, null))
+ ldapManager.getUsers(null) >> users
LdapUserResponse response = new LdapUserResponse("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", null)
ldapManager.createLdapUserResponse(_) >> response
def queryService = Mock(QueryService)
@@ -92,7 +92,7 @@ class LdapListUsersCmdSpec extends spock.lang.Specification {
queryService.searchForUsers(_) >> queryServiceResponse
- def ldapUser = new LdapUser("rmurphy", "rmurphy@cloudstack.org", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", null, false)
+ def ldapUser = new LdapUser("rmurphy", "rmurphy@cloudstack.org", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", null, false, null)
def ldapListUsersCmd = new LdapListUsersCmd(ldapManager,queryService)
when: "isACloudstackUser is executed"
@@ -109,7 +109,7 @@ class LdapListUsersCmdSpec extends spock.lang.Specification {
queryService.searchForUsers(_) >> new ListResponse()
- def ldapUser = new LdapUser("rmurphy", "rmurphy@cloudstack.org", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", null, false)
+ def ldapUser = new LdapUser("rmurphy", "rmurphy@cloudstack.org", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", null, false, null)
def ldapListUsersCmd = new LdapListUsersCmd(ldapManager,queryService)
when: "isACloudstackUser is executed"
diff --git a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapManagerImplSpec.groovy b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapManagerImplSpec.groovy
index c9af0020848..238b2790836 100644
--- a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapManagerImplSpec.groovy
+++ b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapManagerImplSpec.groovy
@@ -52,7 +52,7 @@ class LdapManagerImplSpec extends spock.lang.Specification {
ldapContextFactory.createBindContext() >> { throw new NoLdapUserMatchingQueryException() }
def ldapManager = new LdapManagerImpl(ldapConfigurationDao, ldapContextFactory, ldapUserManagerFactory, ldapConfiguration)
when: "We search for a user but there is a bind issue"
- ldapManager.getUser("rmurphy")
+ ldapManager.getUser("rmurphy", null)
then: "an exception is thrown"
thrown NoLdapUserMatchingQueryException
}
@@ -68,7 +68,7 @@ class LdapManagerImplSpec extends spock.lang.Specification {
ldapContextFactory.createBindContext() >> { throw new NamingException() }
def ldapManager = new LdapManagerImpl(ldapConfigurationDao, ldapContextFactory, ldapUserManagerFactory, ldapConfiguration)
when: "We search for a group of users but there is a bind issue"
- ldapManager.getUsers()
+ ldapManager.getUsers(null)
then: "An exception is thrown"
thrown NoLdapUserMatchingQueryException
}
@@ -116,7 +116,7 @@ class LdapManagerImplSpec extends spock.lang.Specification {
def ldapManager = new LdapManagerImpl(ldapConfigurationDao, ldapContextFactory, ldapUserManagerFactory, ldapConfiguration)
when: "A ldap user response is generated"
def result = ldapManager.createLdapUserResponse(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org",
- "engineering", false))
+ "engineering", false, null))
then: "The result of the response should match the given ldap user"
result.username == "rmurphy"
result.email == "rmurphy@test.com"
@@ -136,11 +136,11 @@ class LdapManagerImplSpec extends spock.lang.Specification {
ldapUserManagerFactory.getInstance(_) >> ldapUserManager
ldapContextFactory.createBindContext() >> null
List users = new ArrayList<>();
- users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", null, false))
+ users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", null, false, null))
ldapUserManager.getUsers(_) >> users;
def ldapManager = new LdapManagerImpl(ldapConfigurationDao, ldapContextFactory, ldapUserManagerFactory, ldapConfiguration)
when: "We search for a group of users"
- def result = ldapManager.getUsers()
+ def result = ldapManager.getUsers(null)
then: "A list greater than 0 is returned"
result.size() > 0;
}
@@ -154,10 +154,10 @@ class LdapManagerImplSpec extends spock.lang.Specification {
def ldapConfiguration = Mock(LdapConfiguration)
ldapUserManagerFactory.getInstance(_) >> ldapUserManager
ldapContextFactory.createBindContext() >> null
- ldapUserManager.getUser(_, _) >> new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", null, false)
+ ldapUserManager.getUser(_, _, _) >> new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", null, false, null)
def ldapManager = new LdapManagerImpl(ldapConfigurationDao, ldapContextFactory, ldapUserManagerFactory, ldapConfiguration)
when: "We search for a user"
- def result = ldapManager.getUser("rmurphy")
+ def result = ldapManager.getUser("rmurphy", null)
then: "The user is returned"
result.username == "rmurphy"
result.email == "rmurphy@test.com"
@@ -192,9 +192,9 @@ class LdapManagerImplSpec extends spock.lang.Specification {
ldapUserManagerFactory.getInstance(_) >> ldapUserManager
def ldapConfiguration = Mock(LdapConfiguration)
def ldapManager = Spy(LdapManagerImpl, constructorArgs: [ldapConfigurationDao, ldapContextFactory, ldapUserManagerFactory, ldapConfiguration])
- ldapManager.getUser(_) >> { new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", null) }
+ ldapManager.getUser(_, null) >> { new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", null) }
when: "The user attempts to authenticate with a bad password"
- def result = ldapManager.canAuthenticate("rmurphy", "password")
+ def result = ldapManager.canAuthenticate("rmurphy", "password", null)
then: "The authentication fails"
result == false
}
@@ -210,7 +210,7 @@ class LdapManagerImplSpec extends spock.lang.Specification {
ldapConfigurationDao.findByHostname(_) >> null
def ldapManager = new LdapManagerImpl(ldapConfigurationDao, ldapContextFactory, ldapUserManagerFactory, ldapConfiguration)
when: "A ldap configuration that doesn't exist is deleted"
- ldapManager.deleteConfiguration("localhost")
+ ldapManager.deleteConfiguration("localhost", 0, null)
then: "A exception is thrown"
thrown InvalidParameterValueException
}
@@ -242,9 +242,9 @@ class LdapManagerImplSpec extends spock.lang.Specification {
def ldapConfiguration = Mock(LdapConfiguration)
ldapUserManagerFactory.getInstance(_) >> ldapUserManager
def ldapManager = Spy(LdapManagerImpl, constructorArgs: [ldapConfigurationDao, ldapContextFactory, ldapUserManagerFactory, ldapConfiguration])
- ldapManager.getUser(_) >> { new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", null) }
+ ldapManager.getUser(_, null) >> { new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", null) }
when: "A user authenticates"
- def result = ldapManager.canAuthenticate("rmurphy", "password")
+ def result = ldapManager.canAuthenticate("rmurphy", "password", null)
then: "The result is true"
result == true
}
@@ -265,7 +265,7 @@ class LdapManagerImplSpec extends spock.lang.Specification {
ldapConfigurationDao.remove(_) >> null
def ldapManager = new LdapManagerImpl(ldapConfigurationDao, ldapContextFactory, ldapUserManagerFactory, ldapConfiguration)
when: "A ldap configuration is deleted"
- def result = ldapManager.deleteConfiguration("localhost")
+ def result = ldapManager.deleteConfiguration("localhost", 0, null)
then: "The deleted configuration is returned"
result.hostname == "localhost"
result.port == 389
@@ -282,7 +282,7 @@ class LdapManagerImplSpec extends spock.lang.Specification {
ldapContextFactory.createBindContext() >> null;
List users = new ArrayList();
- users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false))
+ users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false, null))
ldapUserManager.getUsers(_, _) >> users;
def ldapManager = new LdapManagerImpl(ldapConfigurationDao, ldapContextFactory, ldapUserManagerFactory, ldapConfiguration)
@@ -424,11 +424,11 @@ class LdapManagerImplSpec extends spock.lang.Specification {
ldapUserManagerFactory.getInstance(_) >> ldapUserManager
ldapContextFactory.createBindContext() >> null
List users = new ArrayList<>();
- users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", "engineering", false))
+ users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", "engineering", false, null))
ldapUserManager.getUsersInGroup("engineering", _) >> users;
def ldapManager = new LdapManagerImpl(ldapConfigurationDao, ldapContextFactory, ldapUserManagerFactory, ldapConfiguration)
when: "We search for a group of users"
- def result = ldapManager.getUsersInGroup("engineering")
+ def result = ldapManager.getUsersInGroup("engineering", null)
then: "A list greater of size one is returned"
result.size() == 1;
}
@@ -524,7 +524,7 @@ class LdapManagerImplSpec extends spock.lang.Specification {
def type = "GROUP"
def name = "CN=test,DC=citrix,DC=com"
- ldapUserManager.getUser(username, type, name, _) >> new LdapUser(username, "email", "firstname", "lastname", "principal", "domain", true)
+ ldapUserManager.getUser(username, type, name, _) >> new LdapUser(username, "email", "firstname", "lastname", "principal", "domain", true, null)
when:
LdapUser user = ldapManager.getUser(username, type, name)
@@ -574,7 +574,7 @@ class LdapManagerImplSpec extends spock.lang.Specification {
def type = "GROUP"
def name = "CN=test,DC=citrix,DC=com"
- ldapUserManager.getUser(username, type, name, _) >> new LdapUser(username, "email", "firstname", "lastname", "principal", "domain", false)
+ ldapUserManager.getUser(username, type, name, _) >> new LdapUser(username, "email", "firstname", "lastname", "principal", "domain", false, null)
when:
LdapUser user = ldapManager.getUser(username, type, name)
diff --git a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapSearchUserCmdSpec.groovy b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapSearchUserCmdSpec.groovy
index 55510875899..8936024c01b 100644
--- a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapSearchUserCmdSpec.groovy
+++ b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapSearchUserCmdSpec.groovy
@@ -48,7 +48,7 @@ class LdapSearchUserCmdSpec extends spock.lang.Specification {
given: "We have an Ldap manager and ldap user search cmd"
def ldapManager = Mock(LdapManager)
List users = new ArrayList()
- users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", null, false))
+ users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", null, false, null))
ldapManager.searchUsers(_) >> users
LdapUserResponse response = new LdapUserResponse("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,dc=cloudstack,dc=org", null)
ldapManager.createLdapUserResponse(_) >> response
diff --git a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapUserSpec.groovy b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapUserSpec.groovy
index 8ddfc9a23b8..36b37cad9d0 100644
--- a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapUserSpec.groovy
+++ b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LdapUserSpec.groovy
@@ -22,7 +22,7 @@ class LdapUserSpec extends spock.lang.Specification {
def "Testing LdapUsers hashCode generation"() {
given:
- def userA = new LdapUser(usernameA, "", "", "", "", "", false)
+ def userA = new LdapUser(usernameA, "", "", "", "", "", false, null)
expect:
userA.hashCode() == usernameA.hashCode()
where:
@@ -31,8 +31,8 @@ class LdapUserSpec extends spock.lang.Specification {
def "Testing that LdapUser successfully gives the correct result for a compare to"() {
given: "You have created two LDAP user objects"
- def userA = new LdapUser(usernameA, "", "", "", "", "", false)
- def userB = new LdapUser(usernameB, "", "", "", "", "", false)
+ def userA = new LdapUser(usernameA, "", "", "", "", "", false, null)
+ def userB = new LdapUser(usernameB, "", "", "", "", "", false, null)
expect: "That when compared the result is less than or equal to 0"
userA.compareTo(userB) <= 0
where: "The following values are used"
@@ -43,8 +43,8 @@ class LdapUserSpec extends spock.lang.Specification {
def "Testing that LdapUsers equality"() {
given:
- def userA = new LdapUser(usernameA, "", "", "", "", "", false)
- def userB = new LdapUser(usernameB, "", "", "", "", "", false)
+ def userA = new LdapUser(usernameA, "", "", "", "", "", false, null)
+ def userB = new LdapUser(usernameB, "", "", "", "", "", false, null)
expect:
userA.equals(userA) == true
userA.equals(new Object()) == false
@@ -56,7 +56,7 @@ class LdapUserSpec extends spock.lang.Specification {
def "Testing that the username is correctly set with the ldap object"() {
given: "You have created a LDAP user object with a username"
- def user = new LdapUser(username, "", "", "", "", "", false)
+ def user = new LdapUser(username, "", "", "", "", "", false, null)
expect: "The username is equal to the given data source"
user.getUsername() == username
where: "The username is set to "
@@ -65,7 +65,7 @@ class LdapUserSpec extends spock.lang.Specification {
def "Testing the email is correctly set with the ldap object"() {
given: "You have created a LDAP user object with a email"
- def user = new LdapUser("", email, "", "", "", "", false)
+ def user = new LdapUser("", email, "", "", "", "", false, null)
expect: "The email is equal to the given data source"
user.getEmail() == email
where: "The email is set to "
@@ -74,7 +74,7 @@ class LdapUserSpec extends spock.lang.Specification {
def "Testing the firstname is correctly set with the ldap object"() {
given: "You have created a LDAP user object with a firstname"
- def user = new LdapUser("", "", firstname, "", "", "", false)
+ def user = new LdapUser("", "", firstname, "", "", "", false, null)
expect: "The firstname is equal to the given data source"
user.getFirstname() == firstname
where: "The firstname is set to "
@@ -83,7 +83,7 @@ class LdapUserSpec extends spock.lang.Specification {
def "Testing the lastname is correctly set with the ldap object"() {
given: "You have created a LDAP user object with a lastname"
- def user = new LdapUser("", "", "", lastname, "", "", false)
+ def user = new LdapUser("", "", "", lastname, "", "", false, null)
expect: "The lastname is equal to the given data source"
user.getLastname() == lastname
where: "The lastname is set to "
@@ -92,7 +92,7 @@ class LdapUserSpec extends spock.lang.Specification {
def "Testing the principal is correctly set with the ldap object"() {
given: "You have created a LDAP user object with a principal"
- def user = new LdapUser("", "", "", "", principal, "", false)
+ def user = new LdapUser("", "", "", "", principal, "", false, null)
expect: "The principal is equal to the given data source"
user.getPrincipal() == principal
where: "The principal is set to "
@@ -101,7 +101,7 @@ class LdapUserSpec extends spock.lang.Specification {
def "Testing the domain is correctly set with the ldap object"() {
given: "You have created a LDAP user object with a principal"
- def user = new LdapUser("", "", "", "", "", domain, false)
+ def user = new LdapUser("", "", "", "", "", domain, false, null)
expect: "The principal is equal to the given data source"
user.getDomain() == domain
where: "The username is set to "
diff --git a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LinkDomainToLdapCmdSpec.groovy b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LinkDomainToLdapCmdSpec.groovy
index bad41e82805..46b00a93d6c 100644
--- a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LinkDomainToLdapCmdSpec.groovy
+++ b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/LinkDomainToLdapCmdSpec.groovy
@@ -79,7 +79,7 @@ class LinkDomainToLdapCmdSpec extends Specification {
LinkDomainToLdapResponse response = new LinkDomainToLdapResponse(domainId, type, name, (short)accountType)
_ldapManager.linkDomainToLdap(_,_,_,_) >> response
- _ldapManager.getUser(username, type, name) >> new LdapUser(username, "admin@ccp.citrix.com", "Admin", "Admin", name, "ccp", true)
+ _ldapManager.getUser(username, type, name) >> new LdapUser(username, "admin@ccp.citrix.com", "Admin", "Admin", name, "ccp", true, null)
linkDomainToLdapCmd.admin = username
linkDomainToLdapCmd.type = type
@@ -107,7 +107,7 @@ class LinkDomainToLdapCmdSpec extends Specification {
LinkDomainToLdapResponse response = new LinkDomainToLdapResponse(domainId.toString(), type, name, (short)accountType)
_ldapManager.linkDomainToLdap(_,_,_,_) >> response
- _ldapManager.getUser(username, type, name) >> new LdapUser(username, "admin@ccp.citrix.com", "Admin", "Admin", name, "ccp", false)
+ _ldapManager.getUser(username, type, name) >> new LdapUser(username, "admin@ccp.citrix.com", "Admin", "Admin", name, "ccp", false, null)
_accountService.getActiveAccountByName(username, domainId) >> Mock(Account)
@@ -204,7 +204,7 @@ class LinkDomainToLdapCmdSpec extends Specification {
LinkDomainToLdapResponse response = new LinkDomainToLdapResponse(domainId.toString(), type, name, (short)accountType)
_ldapManager.linkDomainToLdap(_,_,_,_) >> response
- _ldapManager.getUser(username, type, name) >> new LdapUser(username, "admin@ccp.citrix.com", "Admin", "Admin", name, "ccp", false)
+ _ldapManager.getUser(username, type, name) >> new LdapUser(username, "admin@ccp.citrix.com", "Admin", "Admin", name, "ccp", false, null)
_accountService.getActiveAccountByName(username, domainId) >> null
UserAccount userAccount = Mock(UserAccount)
diff --git a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/OpenLdapUserManagerSpec.groovy b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/OpenLdapUserManagerSpec.groovy
index cb08c8fd47c..40daa4110fc 100644
--- a/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/OpenLdapUserManagerSpec.groovy
+++ b/plugins/user-authenticators/ldap/test/groovy/org/apache/cloudstack/ldap/OpenLdapUserManagerSpec.groovy
@@ -17,14 +17,12 @@
package groovy.org.apache.cloudstack.ldap
import org.apache.cloudstack.ldap.LdapConfiguration
-import org.apache.cloudstack.ldap.LdapUserManager
import org.apache.cloudstack.ldap.OpenLdapUserManagerImpl
import spock.lang.Shared
import javax.naming.NamingException
import javax.naming.directory.Attribute
import javax.naming.directory.Attributes
-import javax.naming.directory.InitialDirContext
import javax.naming.directory.SearchControls
import javax.naming.directory.SearchResult
import javax.naming.ldap.InitialLdapContext
@@ -167,12 +165,12 @@ class OpenLdapUserManagerSpec extends spock.lang.Specification {
ldapConfiguration.getEmailAttribute() >> "mail"
ldapConfiguration.getFirstnameAttribute() >> "givenname"
ldapConfiguration.getLastnameAttribute() >> "sn"
- ldapConfiguration.getBaseDn() >> "dc=cloudstack,dc=org"
+ ldapConfiguration.getBaseDn(_) >> "dc=cloudstack,dc=org"
ldapConfiguration.getCommonNameAttribute() >> "cn"
ldapConfiguration.getGroupObject() >> "groupOfUniqueNames"
- ldapConfiguration.getGroupUniqueMemeberAttribute() >> "uniquemember"
+ ldapConfiguration.getGroupUniqueMemberAttribute(_) >> "uniquemember"
ldapConfiguration.getLdapPageSize() >> 1
- ldapConfiguration.getReadTimeout() >> 1000
+ ldapConfiguration.getReadTimeout(_) >> 1000
username = "rmurphy"
email = "rmurphy@test.com"
@@ -186,7 +184,7 @@ class OpenLdapUserManagerSpec extends spock.lang.Specification {
def attributes = createUserAttributes(username, email, firstname, lastname)
def search = createSearchResult(attributes)
def userManager = new OpenLdapUserManagerImpl(ldapConfiguration)
- def result = userManager.createUser(search)
+ def result = userManager.createUser(search,)
expect: "The crated user the data supplied from LDAP"
@@ -290,7 +288,7 @@ class OpenLdapUserManagerSpec extends spock.lang.Specification {
def ldapUserManager = new OpenLdapUserManagerImpl(ldapConfiguration)
when: "A request for users is made"
- def result = ldapUserManager.getUsersInGroup("engineering", createGroupSearchContextOneUser())
+ def result = ldapUserManager.getUsersInGroup("engineering", createGroupSearchContextOneUser(),)
then: "one user is returned"
result.size() == 1
}
@@ -300,7 +298,7 @@ class OpenLdapUserManagerSpec extends spock.lang.Specification {
def ldapUserManager = new OpenLdapUserManagerImpl(ldapConfiguration)
when: "A request for users is made"
- def result = ldapUserManager.getUsersInGroup("engineering", createGroupSearchContextNoUser())
+ def result = ldapUserManager.getUsersInGroup("engineering", createGroupSearchContextNoUser(),)
then: "no user is returned"
result.size() == 0
}
diff --git a/plugins/user-authenticators/ldap/test/org/apache/cloudstack/api/command/LdapConfigurationChanger.java b/plugins/user-authenticators/ldap/test/org/apache/cloudstack/api/command/LdapConfigurationChanger.java
new file mode 100644
index 00000000000..61aa959e81a
--- /dev/null
+++ b/plugins/user-authenticators/ldap/test/org/apache/cloudstack/api/command/LdapConfigurationChanger.java
@@ -0,0 +1,56 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements. See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership. The ASF 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.apache.cloudstack.api.command;
+
+import java.lang.reflect.Field;
+
+interface LdapConfigurationChanger {
+ /**
+ * sets a possibly not accessible field of the target object.
+ * @param target the object to set a hidden fields value in.
+ * @param name the name of the field to set.
+ * @param o intended value for the field "name"
+ * @throws IllegalAccessException
+ * @throws NoSuchFieldException
+ */
+ default void setHiddenField(Object target, final String name, final Object o) throws IllegalAccessException, NoSuchFieldException {
+ Class> klas = target.getClass();
+ Field f = getFirstFoundField(name, klas);
+ f.setAccessible(true);
+ f.set(target, o);
+ }
+
+ /**
+ * the first field found by this name in the class "klas" or any of it's superclasses except for {@code Object}. Implementers of this interface can decide to also return any field in implemented interfaces or in {@code Object}.
+ *
+ * @param name of the field to find
+ * @param klas class to gat a field by name "name" from
+ * @return a {@code Field} by the name "name"
+ * @throws NoSuchFieldException
+ */
+ default Field getFirstFoundField(String name, Class> klas) throws NoSuchFieldException {
+ try {
+ return klas.getDeclaredField(name);
+ } catch (NoSuchFieldException e) {
+ Class> parent = klas.getSuperclass();
+ if(parent.equals(Object.class)) {
+ throw e;
+ }
+ return getFirstFoundField(name, parent);
+ }
+ }
+}
\ No newline at end of file
diff --git a/plugins/user-authenticators/ldap/test/org/apache/cloudstack/api/command/LdapCreateAccountCmdTest.java b/plugins/user-authenticators/ldap/test/org/apache/cloudstack/api/command/LdapCreateAccountCmdTest.java
new file mode 100644
index 00000000000..a4eccbf0856
--- /dev/null
+++ b/plugins/user-authenticators/ldap/test/org/apache/cloudstack/api/command/LdapCreateAccountCmdTest.java
@@ -0,0 +1,72 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements. See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership. The ASF 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.apache.cloudstack.api.command;
+
+import com.cloud.user.Account;
+import com.cloud.user.AccountService;
+import org.apache.cloudstack.acl.RoleService;
+import org.apache.cloudstack.api.ServerApiException;
+import org.apache.cloudstack.ldap.LdapManager;
+import org.apache.cloudstack.ldap.LdapUser;
+import org.apache.cloudstack.ldap.NoLdapUserMatchingQueryException;
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.mockito.Mock;
+import org.mockito.runners.MockitoJUnitRunner;
+
+import static org.junit.Assert.fail;
+import static org.mockito.Matchers.anyString;
+import static org.mockito.Matchers.isNull;
+import static org.powermock.api.mockito.PowerMockito.spy;
+import static org.powermock.api.mockito.PowerMockito.when;
+
+@RunWith(MockitoJUnitRunner.class)
+public class LdapCreateAccountCmdTest implements LdapConfigurationChanger {
+ @Mock
+ LdapManager ldapManager;
+ @Mock
+ AccountService accountService;
+ @Mock
+ RoleService roleService;
+
+ LdapCreateAccountCmd ldapCreateAccountCmd;
+
+ @Before
+ public void setUp() throws NoSuchFieldException, IllegalAccessException {
+ ldapCreateAccountCmd = spy(new LdapCreateAccountCmd(ldapManager, accountService));
+ ldapCreateAccountCmd.roleService = roleService;
+ setHiddenField(ldapCreateAccountCmd,"accountType", Account.ACCOUNT_TYPE_DOMAIN_ADMIN);
+ }
+
+ @Test(expected = ServerApiException.class)
+ public void failureToRetrieveLdapUser() throws Exception {
+ // We have an LdapManager, AccountService and LdapCreateAccountCmd and LDAP user that doesn't exist
+ when(ldapManager.getUser(anyString(), isNull(Long.class))).thenThrow(NoLdapUserMatchingQueryException.class);
+ ldapCreateAccountCmd.execute();
+ fail("An exception should have been thrown: " + ServerApiException.class);
+ }
+
+ @Test(expected = ServerApiException.class)
+ public void failedCreationDueToANullResponseFromCloudstackAccountCreater() throws Exception {
+ // We have an LdapManager, AccountService and LdapCreateAccountCmd
+ LdapUser mrMurphy = new LdapUser("rmurphy", "rmurphy@cloudstack.org", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false, null);
+ when(ldapManager.getUser(anyString(), isNull(Long.class))).thenReturn(mrMurphy);
+ ldapCreateAccountCmd.execute();
+ fail("An exception should have been thrown: " + ServerApiException.class);
+ }
+}
\ No newline at end of file
diff --git a/plugins/user-authenticators/ldap/test/org/apache/cloudstack/api/command/LdapImportUsersCmdTest.java b/plugins/user-authenticators/ldap/test/org/apache/cloudstack/api/command/LdapImportUsersCmdTest.java
new file mode 100644
index 00000000000..8db26733210
--- /dev/null
+++ b/plugins/user-authenticators/ldap/test/org/apache/cloudstack/api/command/LdapImportUsersCmdTest.java
@@ -0,0 +1,85 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements. See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership. The ASF 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.apache.cloudstack.api.command;
+
+import com.cloud.domain.Domain;
+import com.cloud.domain.DomainVO;
+import com.cloud.user.Account;
+import com.cloud.user.AccountService;
+import com.cloud.user.DomainService;
+import org.apache.cloudstack.acl.RoleService;
+import org.apache.cloudstack.api.response.ListResponse;
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.mockito.Mock;
+import org.mockito.runners.MockitoJUnitRunner;
+import org.apache.cloudstack.api.response.LdapUserResponse;
+import org.apache.cloudstack.ldap.LdapManager;
+import org.apache.cloudstack.ldap.LdapUser;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.UUID;
+
+import static junit.framework.TestCase.assertEquals;
+import static org.mockito.Matchers.any;
+import static org.mockito.Matchers.anyString;
+import static org.mockito.Matchers.eq;
+import static org.powermock.api.mockito.PowerMockito.spy;
+import static org.powermock.api.mockito.PowerMockito.when;
+
+@RunWith(MockitoJUnitRunner.class)
+public class LdapImportUsersCmdTest implements LdapConfigurationChanger {
+ @Mock
+ LdapManager ldapManager;
+ @Mock
+ AccountService accountService;
+ @Mock
+ DomainService domainService;
+ @Mock
+ RoleService roleService;
+
+ LdapImportUsersCmd ldapImportUsersCmd;
+
+ @Before
+ public void setUp() throws NoSuchFieldException, IllegalAccessException {
+ ldapImportUsersCmd = spy(new LdapImportUsersCmd(ldapManager, domainService, accountService));
+ ldapImportUsersCmd.roleService = roleService;
+ setHiddenField(ldapImportUsersCmd, "accountType", Account.ACCOUNT_TYPE_DOMAIN_ADMIN);
+ }
+
+ @Test
+ public void successfulResponseFromExecute() throws Exception {
+ List users = new ArrayList();
+ users.add(new LdapUser("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering", false, null));
+ users.add(new LdapUser("bob", "bob@test.com", "Robert", "Young", "cn=bob,ou=engineering,dc=cloudstack,dc=org", "engineering", false, null));
+ when(ldapManager.getUsers(null)).thenReturn(users);
+ LdapUserResponse response1 = new LdapUserResponse("rmurphy", "rmurphy@test.com", "Ryan", "Murphy", "cn=rmurphy,ou=engineering,dc=cloudstack,dc=org", "engineering");
+ LdapUserResponse response2 = new LdapUserResponse("bob", "bob@test.com", "Robert", "Young", "cn=bob,ou=engineering,dc=cloudstack,dc=org", "engineering");
+ when(ldapManager.createLdapUserResponse(any(LdapUser.class))).thenReturn(response1).thenReturn(response2);
+
+
+ Domain domain = new DomainVO("engineering", 1L, 1L, "engineering", UUID.randomUUID().toString());
+ when(domainService.getDomainByName("engineering", 1L)).thenReturn(null, domain);
+ when(domainService.createDomain(eq("engineering"), eq(1L), eq("engineering"), anyString())).thenReturn(domain);
+
+ ldapImportUsersCmd.execute();
+ ListResponse resp = (ListResponse)ldapImportUsersCmd.getResponseObject();
+ assertEquals(" when LdapListUsersCmd is executed, a list of size 2 should be returned", 2, resp.getResponses().size());
+ }
+}
\ No newline at end of file
diff --git a/plugins/user-authenticators/ldap/test/org/apache/cloudstack/api/command/LinkAccountToLdapCmdTest.java b/plugins/user-authenticators/ldap/test/org/apache/cloudstack/api/command/LinkAccountToLdapCmdTest.java
new file mode 100644
index 00000000000..35aed6a50cf
--- /dev/null
+++ b/plugins/user-authenticators/ldap/test/org/apache/cloudstack/api/command/LinkAccountToLdapCmdTest.java
@@ -0,0 +1,97 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements. See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership. The ASF 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.apache.cloudstack.api.command;
+
+import com.cloud.user.Account;
+import com.cloud.user.AccountService;
+import com.cloud.user.User;
+import com.cloud.user.UserAccountVO;
+import org.apache.cloudstack.acl.RoleType;
+import org.apache.cloudstack.api.response.LinkAccountToLdapResponse;
+import org.apache.cloudstack.ldap.LdapManager;
+import org.apache.cloudstack.ldap.LdapUser;
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.mockito.Mock;
+import org.mockito.runners.MockitoJUnitRunner;
+
+import static org.junit.Assert.assertEquals;
+import static org.mockito.Matchers.anyString;
+import static org.mockito.Matchers.eq;
+import static org.mockito.Matchers.isNull;
+import static org.powermock.api.mockito.PowerMockito.when;
+
+@RunWith(MockitoJUnitRunner.class)
+public class LinkAccountToLdapCmdTest implements LdapConfigurationChanger {
+
+ @Mock
+ LdapManager ldapManager;
+ @Mock
+ AccountService accountService;
+
+ LinkAccountToLdapCmd linkAccountToLdapCmd;
+
+ @Before
+ public void setUp() throws NoSuchFieldException, IllegalAccessException {
+ linkAccountToLdapCmd = new LinkAccountToLdapCmd();
+ setHiddenField(linkAccountToLdapCmd, "_ldapManager", ldapManager);
+ setHiddenField(linkAccountToLdapCmd, "_accountService", accountService);
+ }
+
+ @Test
+ public void execute() throws Exception {
+ // test with valid params and with admin who doesnt exist in cloudstack
+ long domainId = 1;
+ String type = "GROUP";
+ String ldapDomain = "CN=test,DC=ccp,DC=Citrix,DC=com";
+ short accountType = Account.ACCOUNT_TYPE_DOMAIN_ADMIN;
+ String username = "admin";
+ long accountId = 24;
+ String accountName = "test";
+
+ setHiddenField(linkAccountToLdapCmd, "ldapDomain", ldapDomain);
+ setHiddenField(linkAccountToLdapCmd, "admin", username);
+ setHiddenField(linkAccountToLdapCmd, "type", type);
+ setHiddenField(linkAccountToLdapCmd, "domainId", domainId);
+ setHiddenField(linkAccountToLdapCmd, "accountType", accountType);
+ setHiddenField(linkAccountToLdapCmd, "accountName", accountName);
+
+
+ LinkAccountToLdapResponse response = new LinkAccountToLdapResponse(String.valueOf(domainId), type, ldapDomain, (short)accountType, username, accountName);
+ when(ldapManager.linkAccountToLdap(linkAccountToLdapCmd)).thenReturn(response);
+ when(ldapManager.getUser(username, type, ldapDomain, 1L))
+ .thenReturn(new LdapUser(username, "admin@ccp.citrix.com", "Admin", "Admin", ldapDomain, "ccp", false, null));
+
+ when(accountService.getActiveAccountByName(username, domainId)).thenReturn(null);
+ UserAccountVO userAccount = new UserAccountVO();
+ userAccount.setAccountId(24);
+ when(accountService.createUserAccount(eq(username), eq(""), eq("Admin"), eq("Admin"), eq("admin@ccp.citrix.com"), isNull(String.class),
+ eq(username), eq(Account.ACCOUNT_TYPE_DOMAIN_ADMIN), eq(RoleType.DomainAdmin.getId()), eq(domainId), isNull(String.class),
+ (java.util.Map)isNull(), anyString(), anyString(), eq(User.Source.LDAP))).thenReturn(userAccount);
+
+ linkAccountToLdapCmd.execute();
+ LinkAccountToLdapResponse result = (LinkAccountToLdapResponse)linkAccountToLdapCmd.getResponseObject();
+ assertEquals("objectName", linkAccountToLdapCmd.APINAME, result.getObjectName());
+ assertEquals("commandName", linkAccountToLdapCmd.getCommandName(), result.getResponseName());
+ assertEquals("domainId", String.valueOf(domainId), result.getDomainId());
+ assertEquals("type", type, result.getType());
+ assertEquals("name", ldapDomain, result.getLdapDomain());
+ assertEquals("accountId", String.valueOf(accountId), result.getAdminId());
+ }
+}
diff --git a/plugins/user-authenticators/ldap/test/org/apache/cloudstack/api/command/LinkDomainToLdapCmdTest.java b/plugins/user-authenticators/ldap/test/org/apache/cloudstack/api/command/LinkDomainToLdapCmdTest.java
new file mode 100644
index 00000000000..8f1fa677cb9
--- /dev/null
+++ b/plugins/user-authenticators/ldap/test/org/apache/cloudstack/api/command/LinkDomainToLdapCmdTest.java
@@ -0,0 +1,98 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements. See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership. The ASF 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.apache.cloudstack.api.command;
+
+import com.cloud.user.Account;
+import com.cloud.user.AccountService;
+import com.cloud.user.User;
+import com.cloud.user.UserAccountVO;
+import org.apache.cloudstack.acl.RoleType;
+import org.apache.cloudstack.api.response.LinkDomainToLdapResponse;
+import org.apache.cloudstack.ldap.LdapManager;
+import org.apache.cloudstack.ldap.LdapUser;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.mockito.Mock;
+import org.mockito.runners.MockitoJUnitRunner;
+
+import static org.junit.Assert.assertEquals;
+import static org.mockito.Matchers.anyString;
+import static org.mockito.Matchers.eq;
+import static org.mockito.Matchers.isNull;
+import static org.powermock.api.mockito.PowerMockito.when;
+
+@RunWith(MockitoJUnitRunner.class)
+public class LinkDomainToLdapCmdTest implements LdapConfigurationChanger
+{
+ @Mock
+ LdapManager ldapManager;
+ @Mock
+ AccountService accountService;
+
+ LinkDomainToLdapCmd linkDomainToLdapCmd;
+
+ @Before
+ public void setUp() throws NoSuchFieldException, IllegalAccessException {
+ linkDomainToLdapCmd = new LinkDomainToLdapCmd();
+ setHiddenField(linkDomainToLdapCmd, "_ldapManager", ldapManager);
+ setHiddenField(linkDomainToLdapCmd, "_accountService", accountService);
+ }
+
+ @After
+ public void tearDown() {
+ }
+
+ @Test
+ public void execute() throws Exception {
+// test with valid params and with admin who doesnt exist in cloudstack
+ Long domainId = 1L;
+ String type = "GROUP";
+ String ldapDomain = "CN=test,DC=ccp,DC=Citrix,DC=com";
+ short accountType = Account.ACCOUNT_TYPE_DOMAIN_ADMIN;
+ String username = "admin";
+ long accountId = 24;
+ setHiddenField(linkDomainToLdapCmd, "ldapDomain", ldapDomain);
+ setHiddenField(linkDomainToLdapCmd, "admin", username);
+ setHiddenField(linkDomainToLdapCmd, "type", type);
+ setHiddenField(linkDomainToLdapCmd, "domainId", domainId);
+ setHiddenField(linkDomainToLdapCmd, "accountType", accountType);
+
+ LinkDomainToLdapResponse response = new LinkDomainToLdapResponse(domainId.toString(), type, ldapDomain, (short)accountType);
+ when(ldapManager.linkDomainToLdap(linkDomainToLdapCmd)).thenReturn(response);
+ when(ldapManager.getUser(username, type, ldapDomain, 1L)).thenReturn(new LdapUser(username, "admin@ccp.citrix.com", "Admin", "Admin", ldapDomain, "ccp", false, null));
+
+ when(accountService.getActiveAccountByName(username, domainId)).thenReturn(null);
+ UserAccountVO userAccount = new UserAccountVO();
+ userAccount.setAccountId(24);
+ when(accountService.createUserAccount(eq(username), eq(""), eq("Admin"), eq("Admin"), eq("admin@ccp.citrix.com"), isNull(String.class),
+ eq(username), eq(Account.ACCOUNT_TYPE_DOMAIN_ADMIN), eq(RoleType.DomainAdmin.getId()), eq(domainId), isNull(String.class),
+ (java.util.Map)isNull(), anyString(), anyString(), eq(User.Source.LDAP))).thenReturn(userAccount);
+
+
+ linkDomainToLdapCmd.execute();
+ LinkDomainToLdapResponse result = (LinkDomainToLdapResponse)linkDomainToLdapCmd.getResponseObject();
+ assertEquals("objectName", "LinkDomainToLdap", result.getObjectName());
+ assertEquals("commandName", linkDomainToLdapCmd.getCommandName(), result.getResponseName());
+ assertEquals("domainId", domainId.toString(), result.getDomainId());
+ assertEquals("type", type, result.getType());
+ assertEquals("name", ldapDomain, result.getLdapDomain());
+ assertEquals("accountId", String.valueOf(accountId), result.getAdminId());
+ }
+
+}
diff --git a/plugins/user-authenticators/ldap/test/org/apache/cloudstack/ldap/LdapConfigurationTest.java b/plugins/user-authenticators/ldap/test/org/apache/cloudstack/ldap/LdapConfigurationTest.java
new file mode 100644
index 00000000000..52c70ac0d19
--- /dev/null
+++ b/plugins/user-authenticators/ldap/test/org/apache/cloudstack/ldap/LdapConfigurationTest.java
@@ -0,0 +1,141 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements. See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership. The ASF 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.apache.cloudstack.ldap;
+
+import org.apache.cloudstack.framework.config.ConfigKey;
+import org.apache.cloudstack.ldap.dao.LdapConfigurationDao;
+import org.apache.cloudstack.ldap.dao.LdapConfigurationDaoImpl;
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.mockito.runners.MockitoJUnitRunner;
+
+import java.lang.reflect.Field;
+import java.lang.reflect.Modifier;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertTrue;
+
+@RunWith(MockitoJUnitRunner.class)
+public class LdapConfigurationTest {
+
+ LdapConfigurationDao ldapConfigurationDao;
+ LdapConfiguration ldapConfiguration;
+
+ private void overrideConfigValue(final String configKeyName, final Object o) throws IllegalAccessException, NoSuchFieldException {
+ Field configKey = LdapConfiguration.class.getDeclaredField(configKeyName);
+ configKey.setAccessible(true);
+
+ ConfigKey key = (ConfigKey)configKey.get(ldapConfiguration);
+
+ Field modifiersField = Field.class.getDeclaredField("modifiers");
+ modifiersField.setAccessible(true);
+ modifiersField.setInt(configKey, configKey.getModifiers() & ~Modifier.FINAL);
+
+ Field f = ConfigKey.class.getDeclaredField("_value");
+ f.setAccessible(true);
+ modifiersField.setInt(f, f.getModifiers() & ~Modifier.FINAL);
+ f.set(key, o);
+
+ Field dynamic = ConfigKey.class.getDeclaredField("_isDynamic");
+ dynamic.setAccessible(true);
+ modifiersField.setInt(dynamic, dynamic.getModifiers() & ~Modifier.FINAL);
+ dynamic.setBoolean(key, false);
+ }
+
+ @Before
+ public void init() throws Exception {
+ ldapConfigurationDao = new LdapConfigurationDaoImpl();
+ ldapConfiguration = new LdapConfiguration(ldapConfigurationDao);;
+ }
+
+ @Test
+ public void getAuthenticationReturnsSimple() throws Exception {
+ overrideConfigValue("ldapBindPrincipal", "cn=bla");
+ overrideConfigValue("ldapBindPassword", "pw");
+ String authentication = ldapConfiguration.getAuthentication(null);
+ assertEquals("authentication should be set to simple", "simple", authentication);
+ }
+
+
+ @Test
+ public void getBaseDnReturnsABaseDn() throws Exception {
+ overrideConfigValue("ldapBaseDn", "dc=cloudstack,dc=org");
+ String baseDn = ldapConfiguration.getBaseDn(null);
+ assertEquals("The set baseDn should be returned","dc=cloudstack,dc=org", baseDn);
+ }
+
+ @Test
+ public void getGroupUniqueMemberAttribute() throws Exception {
+ String [] groupNames = {"bla", "uniquemember", "memberuid", "", null};
+ for (String groupObject: groupNames) {
+ overrideConfigValue("ldapGroupUniqueMemberAttribute", groupObject);
+ String expectedResult = null;
+ if(groupObject == null) {
+ expectedResult = "uniquemember";
+ } else {
+ expectedResult = groupObject;
+ };
+ String result = ldapConfiguration.getGroupUniqueMemberAttribute(null);
+ assertEquals("testing for " + groupObject, expectedResult, result);
+ }
+ }
+
+ @Test
+ public void getSSLStatusCanBeTrue() throws Exception {
+// given: "We have a ConfigDao with values for truststore and truststore password set"
+ overrideConfigValue("ldapTrustStore", "/tmp/ldap.ts");
+ overrideConfigValue("ldapTrustStorePassword", "password");
+
+ assertTrue("A request is made to get the status of SSL should result in true", ldapConfiguration.getSSLStatus());
+ }
+ @Test
+ public void getSearchGroupPrincipleReturnsSuccessfully() throws Exception {
+ // We have a ConfigDao with a value for ldap.search.group.principle and an LdapConfiguration
+ overrideConfigValue("ldapSearchGroupPrinciple", "cn=cloudstack,cn=users,dc=cloudstack,dc=org");
+ String result = ldapConfiguration.getSearchGroupPrinciple(null);
+
+ assertEquals("The result holds the same value configDao did", "cn=cloudstack,cn=users,dc=cloudstack,dc=org",result);
+ }
+
+ @Test
+ public void getTrustStorePasswordResopnds() throws Exception {
+ // We have a ConfigDao with a value for truststore password
+ overrideConfigValue("ldapTrustStorePassword", "password");
+
+ String result = ldapConfiguration.getTrustStorePassword();
+
+ assertEquals("The result is password", "password", result);
+ }
+
+
+ @Test
+ public void getGroupObject() throws Exception {
+ String [] groupNames = {"bla", "groupOfUniqueNames", "groupOfNames", "", null};
+ for (String groupObject: groupNames) {
+ overrideConfigValue("ldapGroupObject", groupObject);
+ String expectedResult = null;
+ if(groupObject == null) {
+ expectedResult = "groupOfUniqueNames";
+ } else {
+ expectedResult = groupObject;
+ };
+ String result = ldapConfiguration.getGroupObject(null);
+ assertEquals("testing for " + groupObject, expectedResult, result);
+ }
+ }
+}
\ No newline at end of file
diff --git a/server/src/com/cloud/configuration/Config.java b/server/src/com/cloud/configuration/Config.java
index a8e24a47806..16be9cee799 100644
--- a/server/src/com/cloud/configuration/Config.java
+++ b/server/src/com/cloud/configuration/Config.java
@@ -39,6 +39,10 @@ import com.cloud.template.TemplateManager;
import com.cloud.vm.UserVmManager;
import com.cloud.vm.snapshot.VMSnapshotManager;
+/**
+ * @deprecated use the more dynamic ConfigKey
+ */
+@Deprecated
public enum Config {
// Alert
@@ -1814,42 +1818,6 @@ public enum Config {
+ "If it is set to -1, then it means always use single-part upload to upload object to S3. ",
null),
- // Ldap
- LdapBasedn("Advanced", ManagementServer.class, String.class, "ldap.basedn", null, "Sets the basedn for LDAP", null),
- LdapBindPassword("Advanced", ManagementServer.class, String.class, "ldap.bind.password", null, "Sets the bind password for LDAP", null),
- LdapBindPrincipal("Advanced", ManagementServer.class, String.class, "ldap.bind.principal", null, "Sets the bind principal for LDAP", null),
- LdapEmailAttribute("Advanced", ManagementServer.class, String.class, "ldap.email.attribute", "mail", "Sets the email attribute used within LDAP", null),
- LdapFirstnameAttribute(
- "Advanced",
- ManagementServer.class,
- String.class,
- "ldap.firstname.attribute",
- "givenname",
- "Sets the firstname attribute used within LDAP",
- null),
- LdapLastnameAttribute("Advanced", ManagementServer.class, String.class, "ldap.lastname.attribute", "sn", "Sets the lastname attribute used within LDAP", null),
- LdapUsernameAttribute("Advanced", ManagementServer.class, String.class, "ldap.username.attribute", "uid", "Sets the username attribute used within LDAP", null),
- LdapUserObject("Advanced", ManagementServer.class, String.class, "ldap.user.object", "inetOrgPerson", "Sets the object type of users within LDAP", null),
- LdapSearchGroupPrinciple(
- "Advanced",
- ManagementServer.class,
- String.class,
- "ldap.search.group.principle",
- null,
- "Sets the principle of the group that users must be a member of",
- null),
- LdapTrustStore("Advanced", ManagementServer.class, String.class, "ldap.truststore", null, "Sets the path to the truststore to use for SSL", null),
- LdapTrustStorePassword("Advanced", ManagementServer.class, String.class, "ldap.truststore.password", null, "Sets the password for the truststore", null),
- LdapGroupObject("Advanced", ManagementServer.class, String.class, "ldap.group.object", "groupOfUniqueNames", "Sets the object type of groups within LDAP", null),
- LdapGroupUniqueMemberAttribute(
- "Advanced",
- ManagementServer.class,
- String.class,
- "ldap.group.user.uniquemember",
- "uniquemember",
- "Sets the attribute for uniquemembers within a group",
- null),
-
// VMSnapshots
VMSnapshotMax("Advanced", VMSnapshotManager.class, Integer.class, "vmsnapshot.max", "10", "Maximum vm snapshots for a vm", null),
VMSnapshotCreateWait("Advanced", VMSnapshotManager.class, Integer.class, "vmsnapshot.create.wait", "1800", "In second, timeout for create vm snapshot", null),
@@ -1979,17 +1947,6 @@ public enum Config {
_scope = ConfigKey.Scope.Global.toString();
}
- private Config(String category, Class> componentClass, Class> type, String name, String defaultValue, String description, String range, String scope) {
- _category = category;
- _componentClass = componentClass;
- _type = type;
- _name = name;
- _defaultValue = defaultValue;
- _description = description;
- _range = range;
- _scope = scope;
- }
-
public String getCategory() {
return _category;
}
@@ -2010,10 +1967,6 @@ public enum Config {
return _type;
}
- public Class> getComponentClass() {
- return _componentClass;
- }
-
public String getScope() {
return _scope;
}
@@ -2081,8 +2034,4 @@ public enum Config {
}
return categories;
}
-
- public static List getConfigListByScope(String scope) {
- return s_scopeLevelConfigsMap.get(scope);
- }
}
diff --git a/server/src/com/cloud/configuration/ConfigurationManagerImpl.java b/server/src/com/cloud/configuration/ConfigurationManagerImpl.java
index c3e9e11441e..9d9ac52fae5 100755
--- a/server/src/com/cloud/configuration/ConfigurationManagerImpl.java
+++ b/server/src/com/cloud/configuration/ConfigurationManagerImpl.java
@@ -131,8 +131,10 @@ import com.cloud.dc.dao.VlanDao;
import com.cloud.deploy.DataCenterDeployment;
import com.cloud.deploy.DeploymentClusterPlanner;
import com.cloud.domain.Domain;
+import com.cloud.domain.DomainDetailVO;
import com.cloud.domain.DomainVO;
import com.cloud.domain.dao.DomainDao;
+import com.cloud.domain.dao.DomainDetailsDao;
import com.cloud.event.ActionEvent;
import com.cloud.event.EventTypes;
import com.cloud.event.UsageEventUtils;
@@ -327,6 +329,8 @@ public class ConfigurationManagerImpl extends ManagerBase implements Configurati
@Inject
AccountDetailsDao _accountDetailsDao;
@Inject
+ DomainDetailsDao _domainDetailsDao;
+ @Inject
PrimaryDataStoreDao _storagePoolDao;
@Inject
NicSecondaryIpDao _nicSecondaryIpDao;
@@ -548,6 +552,21 @@ public class ConfigurationManagerImpl extends ManagerBase implements Configurati
_imageStoreDetailsDao.addDetail(resourceId, name, value, true);
break;
+ case Domain:
+ final DomainVO domain = _domainDao.findById(resourceId);
+ if (domain == null) {
+ throw new InvalidParameterValueException("unable to find domain by id " + resourceId);
+ }
+ DomainDetailVO domainDetailVO = _domainDetailsDao.findDetail(resourceId, name);
+ if (domainDetailVO == null) {
+ domainDetailVO = new DomainDetailVO(resourceId, name, value);
+ _domainDetailsDao.persist(domainDetailVO);
+ } else {
+ domainDetailVO.setValue(value);
+ _domainDetailsDao.update(domainDetailVO.getId(), domainDetailVO);
+ }
+ break;
+
default:
throw new InvalidParameterValueException("Scope provided is invalid");
}
@@ -655,6 +674,7 @@ public class ConfigurationManagerImpl extends ManagerBase implements Configurati
final Long storagepoolId = cmd.getStoragepoolId();
final Long accountId = cmd.getAccountId();
final Long imageStoreId = cmd.getImageStoreId();
+ final Long domainId = cmd.getDomainId();
CallContext.current().setEventDetails(" Name: " + name + " New Value: " + (name.toLowerCase().contains("password") ? "*****" : value == null ? "" : value));
// check if config value exists
final ConfigurationVO config = _configDao.findByName(name);
@@ -700,6 +720,11 @@ public class ConfigurationManagerImpl extends ManagerBase implements Configurati
id = accountId;
paramCountCheck++;
}
+ if (domainId != null) {
+ scope = ConfigKey.Scope.Domain.toString();
+ id = domainId;
+ paramCountCheck++;
+ }
if (storagepoolId != null) {
scope = ConfigKey.Scope.StoragePool.toString();
id = storagepoolId;
diff --git a/server/src/com/cloud/server/ManagementServerImpl.java b/server/src/com/cloud/server/ManagementServerImpl.java
index c855c34b60f..82a37529b25 100644
--- a/server/src/com/cloud/server/ManagementServerImpl.java
+++ b/server/src/com/cloud/server/ManagementServerImpl.java
@@ -1686,6 +1686,7 @@ public class ManagementServerImpl extends ManagerBase implements ManagementServe
final Long clusterId = cmd.getClusterId();
final Long storagepoolId = cmd.getStoragepoolId();
final Long accountId = cmd.getAccountId();
+ final Long domainId = cmd.getDomainId();
final Long imageStoreId = cmd.getImageStoreId();
String scope = null;
Long id = null;
@@ -1706,6 +1707,11 @@ public class ManagementServerImpl extends ManagerBase implements ManagementServe
id = accountId;
paramCountCheck++;
}
+ if (domainId != null) {
+ scope = ConfigKey.Scope.Domain.toString();
+ id = domainId;
+ paramCountCheck++;
+ }
if (storagepoolId != null) {
scope = ConfigKey.Scope.StoragePool.toString();
id = storagepoolId;
diff --git a/server/src/com/cloud/user/AccountManager.java b/server/src/com/cloud/user/AccountManager.java
index e0e7d3bf12d..e708b040ed9 100644
--- a/server/src/com/cloud/user/AccountManager.java
+++ b/server/src/com/cloud/user/AccountManager.java
@@ -215,4 +215,6 @@ public interface AccountManager extends AccountService, Configurable{
"false",
"This parameter allows the users to enable or disable of showing secret key as a part of response for various APIs. By default it is set to false.",
true);
+
+ boolean moveUser(long id, Long domainId, long accountId);
}
diff --git a/server/src/com/cloud/user/AccountManagerImpl.java b/server/src/com/cloud/user/AccountManagerImpl.java
index fea8b47a0c5..dc9fdc0a9e5 100644
--- a/server/src/com/cloud/user/AccountManagerImpl.java
+++ b/server/src/com/cloud/user/AccountManagerImpl.java
@@ -1702,17 +1702,32 @@ public class AccountManagerImpl extends ManagerBase implements AccountManager, M
@ActionEvent(eventType = EventTypes.EVENT_USER_MOVE, eventDescription = "moving User to a new account")
public boolean moveUser(MoveUserCmd cmd) {
- UserVO user = getValidUserVO(cmd.getId());
+ final Long id = cmd.getId();
+ UserVO user = getValidUserVO(id);
Account oldAccount = _accountDao.findById(user.getAccountId());
checkAccountAndAccess(user, oldAccount);
long domainId = oldAccount.getDomainId();
- long newAccountId = getNewAccountId(cmd, domainId);
+ long newAccountId = getNewAccountId(domainId, cmd.getAccountName(), cmd.getAccountId());
+ return moveUser(user, newAccountId);
+ }
+
+ public boolean moveUser(long id, Long domainId, long accountId) {
+ UserVO user = getValidUserVO(id);
+ Account oldAccount = _accountDao.findById(user.getAccountId());
+ checkAccountAndAccess(user, oldAccount);
+ Account newAccount = _accountDao.findById(accountId);
+ checkIfNotMovingAcrossDomains(domainId, newAccount);
+ return moveUser(user , accountId);
+ }
+
+ private boolean moveUser(UserVO user, long newAccountId) {
if(newAccountId == user.getAccountId()) {
// could do a not silent fail but the objective of the user is reached
return true; // no need to create a new user object for this user
}
+
return Transaction.execute(new TransactionCallback() {
@Override
public Boolean doInTransaction(TransactionStatus status) {
@@ -1721,34 +1736,37 @@ public class AccountManagerImpl extends ManagerBase implements AccountManager, M
user.setUuid(UUID.randomUUID().toString());
_userDao.update(user.getId(),user);
newUser.setAccountId(newAccountId);
- boolean success = _userDao.remove(cmd.getId());
+ boolean success = _userDao.remove(user.getId());
UserVO persisted = _userDao.persist(newUser);
return success && persisted.getUuid().equals(user.getExternalEntity());
}
});
}
- private long getNewAccountId(MoveUserCmd cmd, long domainId) {
+ private long getNewAccountId(long domainId, String accountName, Long accountId) {
Account newAccount = null;
- if (StringUtils.isNotBlank(cmd.getAccountName())) {
+ if (StringUtils.isNotBlank(accountName)) {
if(s_logger.isDebugEnabled()) {
- s_logger.debug("Getting id for account by name '" + cmd.getAccountName() + "' in domain " + domainId);
+ s_logger.debug("Getting id for account by name '" + accountName + "' in domain " + domainId);
}
- newAccount = _accountDao.findEnabledAccount(cmd.getAccountName(), domainId);
+ newAccount = _accountDao.findEnabledAccount(accountName, domainId);
}
- if (newAccount == null && cmd.getAccountId() != null) {
- newAccount = _accountDao.findById(cmd.getAccountId());
+ if (newAccount == null && accountId != null) {
+ newAccount = _accountDao.findById(accountId);
}
if (newAccount == null) {
throw new CloudRuntimeException("no account name or account id. this should have been caught before this point");
}
- long newAccountId = newAccount.getAccountId();
+ checkIfNotMovingAcrossDomains(domainId, newAccount);
+ return newAccount.getAccountId();
+ }
+
+ private void checkIfNotMovingAcrossDomains(long domainId, Account newAccount) {
if(newAccount.getDomainId() != domainId) {
// not in scope
throw new InvalidParameterValueException("moving a user from an account in one domain to an account in annother domain is not supported!");
}
- return newAccountId;
}
private void checkAccountAndAccess(UserVO user, Account account) {
diff --git a/server/test/com/cloud/user/MockAccountManagerImpl.java b/server/test/com/cloud/user/MockAccountManagerImpl.java
index 8ea0473aa36..0a92c1446db 100644
--- a/server/test/com/cloud/user/MockAccountManagerImpl.java
+++ b/server/test/com/cloud/user/MockAccountManagerImpl.java
@@ -123,7 +123,13 @@ public class MockAccountManagerImpl extends ManagerBase implements Manager, Acco
return false;
}
- @Override public boolean moveUser(MoveUserCmd moveUserCmd) {
+ @Override
+ public boolean moveUser(MoveUserCmd moveUserCmd) {
+ return false;
+ }
+
+ @Override
+ public boolean moveUser(long id, Long domainId, long accountId) {
return false;
}
diff --git a/server/test/org/apache/cloudstack/networkoffering/ChildTestConfiguration.java b/server/test/org/apache/cloudstack/networkoffering/ChildTestConfiguration.java
index 92d421c0efb..3ffec4cd020 100644
--- a/server/test/org/apache/cloudstack/networkoffering/ChildTestConfiguration.java
+++ b/server/test/org/apache/cloudstack/networkoffering/ChildTestConfiguration.java
@@ -19,34 +19,6 @@ package org.apache.cloudstack.networkoffering;
import java.io.IOException;
-import com.cloud.network.dao.FirewallRulesDcidrsDaoImpl;
-import com.cloud.storage.StorageManager;
-import org.mockito.Mockito;
-import org.springframework.context.annotation.Bean;
-import org.springframework.context.annotation.ComponentScan;
-import org.springframework.context.annotation.ComponentScan.Filter;
-import org.springframework.context.annotation.Configuration;
-import org.springframework.context.annotation.FilterType;
-import org.springframework.core.type.classreading.MetadataReader;
-import org.springframework.core.type.classreading.MetadataReaderFactory;
-import org.springframework.core.type.filter.TypeFilter;
-
-import org.apache.cloudstack.acl.SecurityChecker;
-import org.apache.cloudstack.affinity.AffinityGroupService;
-import org.apache.cloudstack.affinity.dao.AffinityGroupDao;
-import org.apache.cloudstack.context.CallContext;
-import org.apache.cloudstack.engine.orchestration.service.NetworkOrchestrationService;
-import org.apache.cloudstack.engine.subsystem.api.storage.DataStoreManager;
-import org.apache.cloudstack.framework.config.ConfigDepot;
-import org.apache.cloudstack.framework.config.dao.ConfigurationDao;
-import org.apache.cloudstack.region.PortableIpDaoImpl;
-import org.apache.cloudstack.region.PortableIpRangeDaoImpl;
-import org.apache.cloudstack.region.dao.RegionDaoImpl;
-import org.apache.cloudstack.storage.datastore.db.ImageStoreDaoImpl;
-import org.apache.cloudstack.storage.datastore.db.ImageStoreDetailsDaoImpl;
-import org.apache.cloudstack.storage.datastore.db.PrimaryDataStoreDaoImpl;
-import org.apache.cloudstack.test.utils.SpringUtils;
-
import com.cloud.agent.AgentManager;
import com.cloud.alert.AlertManager;
import com.cloud.api.query.dao.UserAccountJoinDaoImpl;
@@ -67,6 +39,7 @@ import com.cloud.dc.dao.PodVlanDaoImpl;
import com.cloud.dc.dao.PodVlanMapDaoImpl;
import com.cloud.dc.dao.VlanDaoImpl;
import com.cloud.domain.dao.DomainDaoImpl;
+import com.cloud.domain.dao.DomainDetailsDao;
import com.cloud.event.dao.UsageEventDaoImpl;
import com.cloud.host.dao.HostDaoImpl;
import com.cloud.host.dao.HostDetailsDaoImpl;
@@ -79,6 +52,7 @@ import com.cloud.network.StorageNetworkManager;
import com.cloud.network.dao.AccountGuestVlanMapDaoImpl;
import com.cloud.network.dao.FirewallRulesCidrsDaoImpl;
import com.cloud.network.dao.FirewallRulesDaoImpl;
+import com.cloud.network.dao.FirewallRulesDcidrsDaoImpl;
import com.cloud.network.dao.IPAddressDaoImpl;
import com.cloud.network.dao.LoadBalancerDaoImpl;
import com.cloud.network.dao.NetworkDao;
@@ -107,6 +81,7 @@ import com.cloud.server.ConfigurationServer;
import com.cloud.server.ManagementService;
import com.cloud.service.dao.ServiceOfferingDaoImpl;
import com.cloud.service.dao.ServiceOfferingDetailsDaoImpl;
+import com.cloud.storage.StorageManager;
import com.cloud.storage.dao.DiskOfferingDaoImpl;
import com.cloud.storage.dao.SnapshotDaoImpl;
import com.cloud.storage.dao.StoragePoolDetailsDaoImpl;
@@ -123,6 +98,30 @@ import com.cloud.vm.dao.NicDaoImpl;
import com.cloud.vm.dao.NicSecondaryIpDaoImpl;
import com.cloud.vm.dao.UserVmDao;
import com.cloud.vm.dao.VMInstanceDaoImpl;
+import org.apache.cloudstack.acl.SecurityChecker;
+import org.apache.cloudstack.affinity.AffinityGroupService;
+import org.apache.cloudstack.affinity.dao.AffinityGroupDao;
+import org.apache.cloudstack.context.CallContext;
+import org.apache.cloudstack.engine.orchestration.service.NetworkOrchestrationService;
+import org.apache.cloudstack.engine.subsystem.api.storage.DataStoreManager;
+import org.apache.cloudstack.framework.config.ConfigDepot;
+import org.apache.cloudstack.framework.config.dao.ConfigurationDao;
+import org.apache.cloudstack.region.PortableIpDaoImpl;
+import org.apache.cloudstack.region.PortableIpRangeDaoImpl;
+import org.apache.cloudstack.region.dao.RegionDaoImpl;
+import org.apache.cloudstack.storage.datastore.db.ImageStoreDaoImpl;
+import org.apache.cloudstack.storage.datastore.db.ImageStoreDetailsDaoImpl;
+import org.apache.cloudstack.storage.datastore.db.PrimaryDataStoreDaoImpl;
+import org.apache.cloudstack.test.utils.SpringUtils;
+import org.mockito.Mockito;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.ComponentScan;
+import org.springframework.context.annotation.ComponentScan.Filter;
+import org.springframework.context.annotation.Configuration;
+import org.springframework.context.annotation.FilterType;
+import org.springframework.core.type.classreading.MetadataReader;
+import org.springframework.core.type.classreading.MetadataReaderFactory;
+import org.springframework.core.type.filter.TypeFilter;
@Configuration
@ComponentScan(basePackageClasses = {AccountVlanMapDaoImpl.class, DomainVlanMapDaoImpl.class, VolumeDaoImpl.class, HostPodDaoImpl.class, DomainDaoImpl.class, ServiceOfferingDaoImpl.class,
@@ -320,6 +319,11 @@ public class
return Mockito.mock(AccountDetailsDao.class);
}
+ @Bean
+ public DomainDetailsDao domainDetailsDao() {
+ return Mockito.mock(DomainDetailsDao.class);
+ }
+
@Bean
public DataStoreManager dataStoreManager() {
return Mockito.mock(DataStoreManager.class);
diff --git a/ui/scripts/domains.js b/ui/scripts/domains.js
index 704195e08a9..1f65ff4bdae 100644
--- a/ui/scripts/domains.js
+++ b/ui/scripts/domains.js
@@ -457,6 +457,15 @@
}
}
},
+
+ tabFilter: function(args) {
+ var hiddenTabs = [];
+ if(!isAdmin()) {
+ hiddenTabs.push('settings');
+ }
+ return hiddenTabs;
+ },
+
tabs: {
details: {
title: 'label.details',
@@ -638,36 +647,6 @@
domainObj["vmTotal"] = totalVMs;
domainObj["volumeTotal"] = totalVolumes;
- /* $.ajax({
- url: createURL("listVirtualMachines&details=min&domainid=" + domainObj.id),
- async: false,
- dataType: "json",
- success: function(json) {
- var items = json.listvirtualmachinesresponse.virtualmachine;
- var total;
- if (items != null)
- total = items.length;
- else
- total = 0;
- domainObj["vmTotal"] = total;
- }
- });
-
- $.ajax({
- url: createURL("listVolumes&domainid=" + domainObj.id),
- async: false,
- dataType: "json",
- success: function(json) {
- var items = json.listvolumesresponse.volume;
- var total;
- if (items != null)
- total = items.length;
- else
- total = 0;
- domainObj["volumeTotal"] = total;
- }
- });*/
-
$.ajax({
url: createURL("listResourceLimits&domainid=" + domainObj.id),
async: false,
@@ -722,7 +701,58 @@
actionFilter: domainActionfilter
});
}
+ },
+ // Granular settings for domains
+ settings: {
+ title: 'label.settings',
+ custom: cloudStack.uiCustom.granularSettings({
+ dataProvider: function(args) {
+ $.ajax({
+ url: createURL('listConfigurations&domainid=' + args.context.domains[0].id),
+ data: listViewDataProvider(args, {}, { searchBy: 'name' }),
+ success: function(json) {
+ args.response.success({
+ data: json.listconfigurationsresponse.configuration
+ });
+
+ },
+
+ error: function(json) {
+ args.response.error(parseXMLHttpResponse(json));
+
+ }
+ });
+
+ },
+ actions: {
+ edit: function(args) {
+ // call updateDomainLevelParameters
+ var data = {
+ name: args.data.jsonObj.name,
+ value: args.data.value
+ };
+
+ $.ajax({
+ url: createURL('updateConfiguration&domainid=' + args.context.domains[0].id),
+ data: data,
+ success: function(json) {
+ var item = json.updateconfigurationresponse.configuration;
+ args.response.success({
+ data: item
+ });
+ },
+
+ error: function(json) {
+ args.response.error(parseXMLHttpResponse(json));
+ }
+
+ });
+
+ }
+ }
+ })
}
+
}
},
labelField: 'name',