/* * CDDL HEADER START * * The contents of this file are subject to the terms of the * Common Development and Distribution License, Version 1.0 only * (the "License"). You may not use this file except in compliance * with the License. * * You can obtain a copy of the license at legal-notices/CDDLv1_0.txt * or http://forgerock.org/license/CDDLv1.0.html. * See the License for the specific language governing permissions * and limitations under the License. * * When distributing Covered Code, include this CDDL HEADER in each * file and include the License file at legal-notices/CDDLv1_0.txt. * If applicable, add the following below this CDDL HEADER, with the * fields enclosed by brackets "[]" replaced with your own identifying * information: * Portions Copyright [yyyy] [name of copyright owner] * * CDDL HEADER END * * * Copyright 2007-2008 Sun Microsystems, Inc. * Portions Copyright 2015 ForgeRock AS. */ package org.opends.server.admin.client.ldap; import java.util.Arrays; import java.util.Collection; import java.util.Collections; import java.util.SortedSet; import java.util.TreeSet; import org.opends.server.TestCaseUtils; import org.opends.server.admin.AdminTestCase; import org.opends.server.admin.PropertyException; import org.opends.server.admin.TestCfg; import org.opends.server.admin.TestChildCfgClient; import org.opends.server.admin.TestChildCfgDefn; import org.opends.server.admin.TestParentCfgClient; import org.opends.server.admin.client.ManagedObject; import org.opends.server.admin.client.ManagedObjectDecodingException; import org.opends.server.admin.client.ManagementContext; import org.opends.server.admin.std.client.RootCfgClient; import org.opends.server.core.DirectoryServer; import org.testng.Assert; import org.testng.annotations.AfterClass; import org.testng.annotations.BeforeClass; import org.testng.annotations.Test; /** * Test cases for aggregations on the client-side. */ @Test(sequential = true) public class AggregationClientTest extends AdminTestCase { /** Test LDIF. */ private static final String[] TEST_LDIF = new String[] { // Base entries. "dn: cn=config", "objectclass: top", "objectclass: ds-cfg-branch", "cn: config", "", "dn: cn=test parents,cn=config", "objectclass: top", "objectclass: ds-cfg-branch", "cn: test-parents", "", // Parent 1 - uses default values for // optional-multi-valued-dn-property. "dn: cn=test parent 1,cn=test parents,cn=config", "objectclass: top", "objectclass: ds-cfg-test-parent-dummy", "cn: test parent 1", "ds-cfg-enabled: true", "ds-cfg-java-class: org.opends.server.extensions.UserDefinedVirtualAttributeProvider", "ds-cfg-attribute-type: description", "", // Child base entry. "dn:cn=test children,cn=test parent 1,cn=test parents,cn=config", "objectclass: top", "objectclass: ds-cfg-branch", "cn: multiple children", "", // Child 1 has no references. "dn: cn=test child 1,cn=test children,cn=test parent 1,cn=test parents,cn=config", "objectclass: top", "objectclass: ds-cfg-test-child-dummy", "cn: test child 1", "ds-cfg-enabled: true", "ds-cfg-java-class: org.opends.server.extensions.UserDefinedVirtualAttributeProvider", "ds-cfg-attribute-type: description", "", // Child 2 has a single valid reference. "dn: cn=test child 2,cn=test children,cn=test parent 1,cn=test parents,cn=config", "objectclass: top", "objectclass: ds-cfg-test-child-dummy", "cn: test child 2", "ds-cfg-enabled: true", "ds-cfg-java-class: org.opends.server.extensions.UserDefinedVirtualAttributeProvider", "ds-cfg-attribute-type: description", "ds-cfg-rotation-policy: cn=LDAP Connection Handler, cn=connection handlers, cn=config", "", // Child 3 has a multiple valid references. "dn: cn=test child 3,cn=test children,cn=test parent 1,cn=test parents,cn=config", "objectclass: top", "objectclass: ds-cfg-test-child-dummy", "cn: test child 3", "ds-cfg-enabled: true", "ds-cfg-java-class: org.opends.server.extensions.UserDefinedVirtualAttributeProvider", "ds-cfg-attribute-type: description", "ds-cfg-rotation-policy: cn=LDAP Connection Handler, cn=connection handlers, cn=config", "ds-cfg-rotation-policy: cn=LDAPS Connection Handler, cn=connection handlers, cn=config", "", // Child 4 has a single bad reference. "dn: cn=test child 4,cn=test children,cn=test parent 1,cn=test parents,cn=config", "objectclass: top", "objectclass: ds-cfg-test-child-dummy", "cn: test child 4", "ds-cfg-enabled: true", "ds-cfg-java-class: org.opends.server.extensions.UserDefinedVirtualAttributeProvider", "ds-cfg-attribute-type: description", "ds-cfg-rotation-policy: cn=LDAP Connection Handler, cn=bad rdn, cn=config", "", "dn: cn=Connection Handlers,cn=config", "objectClass: top", "objectClass: ds-cfg-branch", "cn: Connection Handlers", "", "dn: cn=LDAP Connection Handler,cn=Connection Handlers,cn=config", "objectClass: top", "objectClass: ds-cfg-connection-handler", "objectClass: ds-cfg-ldap-connection-handler", "cn: LDAP Connection Handler", "ds-cfg-java-class: org.opends.server.protocols.ldap.LDAPConnectionHandler", "ds-cfg-enabled: true", "ds-cfg-listen-address: 0.0.0.0", "ds-cfg-listen-port: 389", "", "dn: cn=LDAPS Connection Handler,cn=Connection Handlers,cn=config", "objectClass: top", "objectClass: ds-cfg-connection-handler", "objectClass: ds-cfg-ldap-connection-handler", "cn: LDAPS Connection Handler", "ds-cfg-java-class: org.opends.server.protocols.ldap.LDAPConnectionHandler", "ds-cfg-enabled: false", "ds-cfg-listen-address: 0.0.0.0", "ds-cfg-listen-port: 636", "ds-cfg-use-ssl: true", "ds-cfg-ssl-client-auth-policy: optional", "ds-cfg-ssl-cert-nickname: server-cert", "ds-cfg-key-manager-provider: cn=JKS,cn=Key Manager Providers,cn=config", "ds-cfg-trust-manager-provider: cn=JKS,cn=Trust Manager Providers,cn=config", "", "dn: cn=JMX Connection Handler,cn=Connection Handlers,cn=config", "objectClass: top", "objectClass: ds-cfg-connection-handler", "objectClass: ds-cfg-jmx-connection-handler", "cn: JMX Connection Handler", "ds-cfg-java-class: org.opends.server.protocols.jmx.JmxConnectionHandler", "ds-cfg-enabled: false", "ds-cfg-listen-port: 1689", "" }; /** * Sets up tests * * @throws Exception * If the server could not be initialized. */ @BeforeClass public void setUp() throws Exception { // This test suite depends on having the schema available, so // we'll start the server. TestCaseUtils.startServer(); TestCfg.setUp(); } /** * Tears down test environment. */ @AfterClass public void tearDown() { TestCfg.cleanup(); } /** * Tests that aggregation contains no values when it contains does * not contain any DN attribute values. * * @throws Exception * If the test unexpectedly fails. */ @Test public void testAggregationEmpty() throws Exception { MockLDAPConnection c = new MockLDAPConnection(); c.importLDIF(TEST_LDIF); ManagementContext ctx = LDAPManagementContext.createFromContext(c); TestParentCfgClient parent = getTestParent(ctx, "test parent 1"); TestChildCfgClient child = parent.getTestChild("test child 1"); assertSetEquals(child.getAggregationProperty(), new String[0]); } /** * Tests that aggregation contains single valid value when it * contains a single valid DN attribute values. * * @throws Exception * If the test unexpectedly fails. */ @Test public void testAggregationSingle() throws Exception { MockLDAPConnection c = new MockLDAPConnection(); c.importLDIF(TEST_LDIF); ManagementContext ctx = LDAPManagementContext.createFromContext(c); TestParentCfgClient parent = getTestParent(ctx, "test parent 1"); TestChildCfgClient child = parent.getTestChild("test child 2"); // Test normalization. assertSetEquals(child.getAggregationProperty(), "LDAP Connection Handler"); assertSetEquals(child.getAggregationProperty(), " LDAP Connection Handler "); assertSetEquals(child.getAggregationProperty(), " ldap connection HANDLER "); } /** * Tests that aggregation contains multiple valid values when it * contains a multiple valid DN attribute values. * * @throws Exception * If the test unexpectedly fails. */ @Test public void testAggregationMultiple() throws Exception { MockLDAPConnection c = new MockLDAPConnection(); c.importLDIF(TEST_LDIF); ManagementContext ctx = LDAPManagementContext.createFromContext(c); TestParentCfgClient parent = getTestParent(ctx, "test parent 1"); TestChildCfgClient child = parent.getTestChild("test child 3"); assertSetEquals(child.getAggregationProperty(), "LDAPS Connection Handler", "LDAP Connection Handler"); } /** * Tests that aggregation is rejected when the LDAP DN contains a * valid RDN but an invalid parent DN. * * @throws Exception * If the test unexpectedly fails. */ @Test public void testAggregationBadBaseDN() throws Exception { MockLDAPConnection c = new MockLDAPConnection(); c.importLDIF(TEST_LDIF); ManagementContext ctx = LDAPManagementContext.createFromContext(c); TestParentCfgClient parent = getTestParent(ctx, "test parent 1"); try { parent.getTestChild("test child 4"); Assert.fail("Unexpectedly retrieved test child 4" + " when it had a bad aggregation value"); } catch (ManagedObjectDecodingException e) { Collection<PropertyException> causes = e.getCauses(); Assert.assertEquals(causes.size(), 1); Throwable cause = causes.iterator().next(); if (cause instanceof PropertyException) { PropertyException pe = (PropertyException) cause; Assert.assertEquals(pe.getPropertyDefinition(), TestChildCfgDefn .getInstance().getAggregationPropertyPropertyDefinition()); } else { // Got an unexpected cause. throw e; } } } /** * Tests creation of a child managed object with a single reference. * * @throws Exception * If an unexpected error occurred. */ @Test public void testCreateChildManagedObject() throws Exception { CreateEntryMockLDAPConnection c = new CreateEntryMockLDAPConnection( "cn=test child new,cn=test children,cn=test parent 1,cn=test parents,cn=config"); c.importLDIF(TEST_LDIF); c.addExpectedAttribute("cn", "test child new"); c.addExpectedAttribute("objectclass", "top", "ds-cfg-test-child-dummy"); c.addExpectedAttribute("ds-cfg-enabled", "true"); c.addExpectedAttribute("ds-cfg-java-class", "org.opends.server.extensions.UserDefinedVirtualAttributeProvider"); c.addExpectedAttribute("ds-cfg-attribute-type", "description"); c.addExpectedAttribute("ds-cfg-rotation-policy", "cn=LDAP Connection Handler,cn=connection handlers,cn=config"); ManagementContext ctx = LDAPManagementContext.createFromContext(c); TestParentCfgClient parent = getTestParent(ctx, "test parent 1"); TestChildCfgClient child = parent.createTestChild(TestChildCfgDefn.getInstance(), "test child new", null); child.setMandatoryBooleanProperty(true); child.setMandatoryReadOnlyAttributeTypeProperty(DirectoryServer.getAttributeTypeOrNull("description")); child.setAggregationProperty(Collections.singleton("LDAP Connection Handler")); child.commit(); c.assertEntryIsCreated(); } /** * Tests modification of a child managed object so that it has a * different reference. * * @throws Exception * If an unexpected error occurred. */ @Test public void testModifyChildManagedObject() throws Exception { ModifyEntryMockLDAPConnection c = new ModifyEntryMockLDAPConnection( "cn=test child 2,cn=test children,cn=test parent 1,cn=test parents,cn=config"); c.importLDIF(TEST_LDIF); c.addExpectedModification("ds-cfg-rotation-policy", "cn=LDAPS Connection Handler,cn=connection handlers,cn=config", "cn=JMX Connection Handler,cn=connection handlers,cn=config"); ManagementContext ctx = LDAPManagementContext.createFromContext(c); TestParentCfgClient parent = getTestParent(ctx, "test parent 1"); TestChildCfgClient child = parent.getTestChild("test child 2"); child.setAggregationProperty(Arrays.asList("LDAPS Connection Handler", "JMX Connection Handler")); child.commit(); Assert.assertTrue(c.isEntryModified()); } /** Retrieve the named test parent managed object. */ private TestParentCfgClient getTestParent(ManagementContext context, String name) throws Exception { ManagedObject<RootCfgClient> root = context.getRootConfigurationManagedObject(); return root.getChild(TestCfg.getTestOneToManyParentRelationDefinition(), name).getConfiguration(); } /** Asserts that the actual set of DNs contains the expected values. */ private void assertSetEquals(SortedSet<String> actual, String... expected) { SortedSet<String> values = new TreeSet<>(TestChildCfgDefn .getInstance().getAggregationPropertyPropertyDefinition()); if (expected != null) { Collections.addAll(values, expected); } Assert.assertEquals((Object) actual, (Object) values); } }