| | |
| | | import org.testng.annotations.AfterClass; |
| | | import org.testng.annotations.BeforeClass; |
| | | import org.testng.annotations.Test; |
| | | |
| | | import static org.opends.server.synchronization.OperationContext.SYNCHROCONTEXT; |
| | | import static org.testng.Assert.*; |
| | | |
| | | import org.opends.server.TestCaseUtils; |
| | |
| | | import org.opends.server.types.Modification; |
| | | import org.opends.server.types.ModificationType; |
| | | import org.opends.server.types.RDN; |
| | | import org.opends.server.types.ResultCode; |
| | | |
| | | /** |
| | | * Test the contructors, encoders and decoders of the synchronization |
| | |
| | | * schema check flag |
| | | */ |
| | | private boolean schemaCheck; |
| | | |
| | | |
| | | // WORKAROUND FOR BUG #639 - BEGIN - |
| | | /** |
| | | * |
| | | */ |
| | | MultimasterSynchronization mms; |
| | | |
| | | // WORKAROUND FOR BUG #639 - END - |
| | | |
| | | |
| | | /** |
| | | * Set up the environment for performing the tests in this Class. |
| | |
| | | // This test suite depends on having the schema available. |
| | | TestCaseUtils.startServer(); |
| | | |
| | | // Disable schema check |
| | | schemaCheck = DirectoryServer.checkSchema(); |
| | | DirectoryServer.setCheckSchema(false); |
| | | connection = new InternalClientConnection(); |
| | | String[] topEntries = new String[3]; |
| | | |
| | | topEntries[0] = "dn: dc=com\n" + "objectClass: top\n" |
| | | + "objectCClasslass: domain\n"; |
| | | topEntries[1] = "dn: dc=example,dc=com\n" + "objectClass: top\n" |
| | | // Create an internal connection |
| | | connection = new InternalClientConnection(); |
| | | |
| | | // Create backend top level entries |
| | | String[] topEntries = new String[2]; |
| | | topEntries[0] = "dn: dc=example,dc=com\n" + "objectClass: top\n" |
| | | + "objectClass: domain\n"; |
| | | topEntries[2] = "dn: ou=People,dc=example,dc=com\n" |
| | | topEntries[1] = "dn: ou=People,dc=example,dc=com\n" |
| | | + "objectClass: top\n" + "objectClass: organizationalUnit\n"; |
| | | |
| | | Entry entry ; |
| | | for (int i = 0; i < 3; i++) |
| | | for (int i = 0; i < topEntries.length; i++) |
| | | { |
| | | entry = TestCaseUtils.entryFromLdifString(topEntries[i]); |
| | | AddOperation addOp = new AddOperation(connection, |
| | |
| | | entryList.add(entry); |
| | | } |
| | | |
| | | // top level synchro entry |
| | | // top level synchro provider |
| | | synchroStringDN = "cn=Synchronization Providers,cn=config"; |
| | | |
| | | // Multimaster Synchro plugin |
| | |
| | | |
| | | DirectoryServer.setCheckSchema(schemaCheck); |
| | | DeleteOperation op; |
| | | |
| | | // WORKAROUND FOR BUG #639 - BEGIN - |
| | | DirectoryServer.deregisterSynchronizationProvider(mms); |
| | | mms.finalizeSynchronizationProvider(); |
| | | // WORKAROUND FOR BUG #639 - END - |
| | | |
| | | // Delete entries |
| | | for (Entry entry : entryList) |
| | | Entry entries[] = entryList.toArray(new Entry[0]) ; |
| | | for (int i = entries.length -1 ; i != 0 ; i--) |
| | | { |
| | | try |
| | | { |
| | | op = new DeleteOperation(connection, InternalClientConnection |
| | | .nextOperationID(), InternalClientConnection.nextMessageID(), |
| | | null, entry.getDN()); |
| | | null, entries[i].getDN()); |
| | | op.run(); |
| | | } |
| | | catch (Exception e) |
| | |
| | | } |
| | | |
| | | /** |
| | | * The First test (just to be sure that the classSetup in called |
| | | * Tests that performed operation will generate synchronization messages |
| | | */ |
| | | @Test() |
| | | public void updateOperations() throws Exception |
| | |
| | | // Add the Multimaster synchronization plugin |
| | | DirectoryServer.getConfigHandler().addEntry(synchroPluginEntry, null); |
| | | entryList.add(synchroPluginEntry); |
| | | assertNotNull(DirectoryServer.getConfigEntry(DN.decode(synchroPluginStringDN))); |
| | | assertNotNull(DirectoryServer.getConfigEntry(DN |
| | | .decode(synchroPluginStringDN)), |
| | | "Unable to add the Multimaster synchronization plugin"); |
| | | |
| | | // WORKAROUND FOR BUG #639 - BEGIN - |
| | | DN dn = DN.decode(synchroPluginStringDN); |
| | | ConfigEntry mmsConfigEntry = DirectoryServer.getConfigEntry(dn); |
| | | MultimasterSynchronization mms = new MultimasterSynchronization(); |
| | | mms = new MultimasterSynchronization(); |
| | | try |
| | | { |
| | | mms.initializeSynchronizationProvider(mmsConfigEntry); |
| | | } |
| | | catch (ConfigException e) |
| | | { |
| | | assertTrue(false); |
| | | assertTrue(false, |
| | | "Unable to initialize the Multimaster synchronization plugin"); |
| | | } |
| | | DirectoryServer.registerSynchronizationProvider(mms); |
| | | // WORKAROUND FOR BUG #639 - BEGIN - |
| | | // WORKAROUND FOR BUG #639 - END - |
| | | |
| | | // |
| | | // Add the changelog server |
| | | DirectoryServer.getConfigHandler().addEntry(changeLogEntry, null); |
| | | assertNotNull(DirectoryServer.getConfigEntry(changeLogEntry.getDN())); |
| | | assertNotNull(DirectoryServer.getConfigEntry(changeLogEntry.getDN()), |
| | | "Unable to add the changeLog server"); |
| | | entryList.add(changeLogEntry); |
| | | |
| | | // |
| | | // We also have a replicated suffix |
| | | // We also have a replicated suffix (synchronization domain) |
| | | DirectoryServer.getConfigHandler().addEntry(synchroServerEntry, null); |
| | | assertNotNull(DirectoryServer.getConfigEntry(synchroServerEntry.getDN())); |
| | | assertNotNull(DirectoryServer.getConfigEntry(synchroServerEntry.getDN()), |
| | | "Unable to add the syncrhonized server"); |
| | | entryList.add(synchroServerEntry); |
| | | |
| | | // |
| | |
| | | + "ds-cfg-changelog-server: localhost:8989\n" |
| | | + "ds-cfg-directory-server-id: 2\n" |
| | | + "ds-cfg-receive-status: true\n"; |
| | | Entry synchroServerEntry2 = TestCaseUtils.entryFromLdifString(synchroServerLdif2); |
| | | ConfigEntry newConfigEntry = new ConfigEntry(synchroServerEntry2,DirectoryServer.getConfigEntry(DN.decode(synchroPluginStringDN))); |
| | | SynchronizationDomain syncDomain2 = new SynchronizationDomain(newConfigEntry); |
| | | Entry synchroServerEntry2 = TestCaseUtils |
| | | .entryFromLdifString(synchroServerLdif2); |
| | | ConfigEntry newConfigEntry = new ConfigEntry(synchroServerEntry2, |
| | | DirectoryServer.getConfigEntry(DN.decode(synchroPluginStringDN))); |
| | | SynchronizationDomain syncDomain2 = new SynchronizationDomain( |
| | | newConfigEntry); |
| | | |
| | | // |
| | | // Create an Entry |
| | | // Create an Entry (add operation) |
| | | AddOperation addOp = new AddOperation(connection, |
| | | InternalClientConnection.nextOperationID(), InternalClientConnection |
| | | .nextMessageID(), null, personEntry.getDN(), personEntry |
| | |
| | | .getOperationalAttributes()); |
| | | addOp.run(); |
| | | entryList.add(personEntry); |
| | | assertNotNull(DirectoryServer.getEntry(personEntry.getDN())); |
| | | assertNotNull(DirectoryServer.getEntry(personEntry.getDN()), |
| | | "The Add Entry operation fails"); |
| | | |
| | | // See if the client has receive the msg |
| | | // Check if the client has receive the msg |
| | | UpdateMessage msg = syncDomain2.receive() ; |
| | | Operation receivedOp = msg.createOperation(connection); |
| | | assertTrue(OperationType.ADD.compareTo(receivedOp.getOperationType()) == 0); |
| | | assertTrue(DN.decode(msg.getDn()).compareTo(personEntry.getDN()) == 0); |
| | | assertTrue(OperationType.ADD.compareTo(receivedOp.getOperationType()) == 0, |
| | | "The received synchronization message is not an ADD msg"); |
| | | assertTrue(DN.decode(msg.getDn()).compareTo(personEntry.getDN()) == 0, |
| | | "The received ADD synchronization message is not for the excepted DN"); |
| | | |
| | | |
| | | // Modify the entry |
| | |
| | | .nextMessageID(), null, personEntry.getDN(), mods); |
| | | modOp.setInternalOperation(true); |
| | | modOp.run(); |
| | | // TODO Check the telephoneNumber attrbiute |
| | | // TODO Check the telephoneNumber attribute |
| | | |
| | | // See if the client has receive the msg |
| | | msg = syncDomain2.receive() ; |
| | | receivedOp = msg.createOperation(connection); |
| | | assertTrue(OperationType.MODIFY.compareTo(receivedOp.getOperationType()) == 0); |
| | | assertTrue(DN.decode(msg.getDn()).compareTo(personEntry.getDN()) == 0); |
| | | assertTrue(OperationType.MODIFY.compareTo(receivedOp.getOperationType()) == 0, |
| | | "The received synchronization message is not a MODIFY msg"); |
| | | assertTrue(DN.decode(msg.getDn()).compareTo(personEntry.getDN()) == 0, |
| | | "The received MODIFY synchronization message is not for the excepted DN"); |
| | | |
| | | // |
| | | // Modify the entry DN |
| | |
| | | ModifyDNOperation modDNOp = new ModifyDNOperation(connection, |
| | | InternalClientConnection.nextOperationID(), InternalClientConnection |
| | | .nextMessageID(), null, personEntry.getDN(), RDN |
| | | .decode("uid=new person"), false, DN |
| | | .decode("uid=new person"), true, DN |
| | | .decode("ou=People,dc=example,dc=com")); |
| | | modDNOp.run(); |
| | | assertNotNull(DirectoryServer.getEntry(newDN)); |
| | | assertNull(DirectoryServer.getEntry(personEntry.getDN())); |
| | | assertNotNull(DirectoryServer.getEntry(newDN), |
| | | "The MOD_DN operation didn't create the new person entry"); |
| | | assertNull(DirectoryServer.getEntry(personEntry.getDN()), |
| | | "The MOD_DN operation didn't delete the old person entry"); |
| | | entryList.add(DirectoryServer.getEntry(newDN)); |
| | | |
| | | // See if the client has receive the msg |
| | | msg = syncDomain2.receive() ; |
| | | receivedOp = msg.createOperation(connection); |
| | | assertTrue(OperationType.MODIFY_DN.compareTo(receivedOp.getOperationType()) == 0); |
| | | assertTrue(DN.decode(msg.getDn()).compareTo(personEntry.getDN()) == 0); |
| | | assertTrue(OperationType.MODIFY_DN.compareTo(receivedOp.getOperationType()) == 0, |
| | | "The received synchronization message is not a MODIFY_DN msg"); |
| | | assertTrue(DN.decode(msg.getDn()).compareTo(personEntry.getDN()) == 0, |
| | | "The received MODIFY_DN synchronization message is not for the excepted DN"); |
| | | |
| | | |
| | | // Delete the entry |
| | | Entry newPersonEntry = DirectoryServer.getEntry(newDN) ; |
| | | DeleteOperation delOp = new DeleteOperation(connection, |
| | | InternalClientConnection.nextOperationID(), InternalClientConnection |
| | | .nextMessageID(), null, DN |
| | | .decode("uid= new person,ou=People,dc=example,dc=com")); |
| | | delOp.run(); |
| | | assertNull(DirectoryServer.getEntry(newDN)); |
| | | assertNull(DirectoryServer.getEntry(newDN), |
| | | "Unable to delete the new person Entry"); |
| | | entryList.remove(newPersonEntry); |
| | | |
| | | // See if the client has receive the msg |
| | | msg = syncDomain2.receive() ; |
| | | receivedOp = msg.createOperation(connection); |
| | | assertTrue(OperationType.DELETE.compareTo(receivedOp.getOperationType()) == 0); |
| | | assertTrue(OperationType.DELETE.compareTo(receivedOp.getOperationType()) == 0, |
| | | "The received synchronization message is not a DELETE msg"); |
| | | assertTrue(DN.decode(msg.getDn()).compareTo(DN |
| | | .decode("uid= new person,ou=People,dc=example,dc=com")) == 0); |
| | | .decode("uid= new person,ou=People,dc=example,dc=com")) == 0, |
| | | "The received DELETE synchronization message is not for the excepted DN"); |
| | | |
| | | // Purge the client |
| | | syncDomain2.shutdown() ; |
| | | |
| | | // |
| | | // Be new Client of the Change log |
| | | // We will check that when we send message to the Chanlog server |
| | | // the synchronization domain apply those changes. |
| | | |
| | | // Create a new synchronization domain |
| | | String synchroServerLdif3 = "dn: cn=example3, " + synchroPluginStringDN + "\n" |
| | | + "objectClass: top\n" |
| | | + "objectClass: ds-cfg-synchronization-provider-config\n" |
| | | + "cn: example\n" |
| | | + "ds-cfg-synchronization-dn: ou=People,dc=example,dc=com\n" |
| | | + "ds-cfg-changelog-server: localhost:8989\n" |
| | | + "ds-cfg-directory-server-id: 3\n" |
| | | + "ds-cfg-receive-status: true\n"; |
| | | Entry synchroServerEntry3 = TestCaseUtils |
| | | .entryFromLdifString(synchroServerLdif3); |
| | | newConfigEntry = new ConfigEntry(synchroServerEntry3, DirectoryServer |
| | | .getConfigEntry(DN.decode(synchroPluginStringDN))); |
| | | SynchronizationDomain syncDomain3 = new SynchronizationDomain( |
| | | newConfigEntry); |
| | | |
| | | // |
| | | // Message to Create the Entry |
| | | addOp = new AddOperation(connection, |
| | | InternalClientConnection.nextOperationID(), InternalClientConnection |
| | | .nextMessageID(), null, personEntry.getDN(), personEntry |
| | | .getObjectClasses(), personEntry.getUserAttributes(), personEntry |
| | | .getOperationalAttributes()); |
| | | syncDomain3.doPreOperation(addOp); |
| | | addOp.setResultCode(ResultCode.SUCCESS) ; |
| | | syncDomain3.synchronize(addOp); |
| | | |
| | | // Wait no more than 1 second (synchro operation has to be sent, |
| | | // received and replay) |
| | | Entry newEntry = null ; |
| | | int i = 10 ; |
| | | while ((i> 0) && (newEntry == null)) |
| | | { |
| | | Thread.sleep(100); |
| | | newEntry = DirectoryServer.getEntry(personEntry.getDN()); |
| | | i-- ; |
| | | } |
| | | newEntry = DirectoryServer.getEntry(personEntry.getDN()); |
| | | assertNotNull(newEntry, |
| | | "The send ADD synchronization message was not applied"); |
| | | entryList.add(newEntry); |
| | | |
| | | // Message to Modify the new created entry |
| | | |
| | | // Unable to test it: the doPreOperation operation use |
| | | // modifyOperation.getModifiedEntry() which cannot be set the |
| | | // the public level. |
| | | // Otherwise, code will look like: |
| | | /* |
| | | modOp = new ModifyOperation(connection, |
| | | InternalClientConnection.nextOperationID(), InternalClientConnection |
| | | .nextMessageID(), null, personEntry.getDN(), mods); |
| | | modOp.setModifiedEntry(...); |
| | | mms.doPreOperation(modOp); |
| | | modOp.setResultCode(ResultCode.SUCCESS) ; |
| | | syncDomain3.synchronize(modOp); |
| | | // TODO Check the telephoneNumber attribute |
| | | */ |
| | | |
| | | // Purge the message sender |
| | | syncDomain3.shutdown() ; |
| | | |
| | | |
| | | // Check synchronization monitoring |
| | | SynchronizationDomain syncDomain = new SynchronizationDomain( |
| | |
| | | ArrayList<Attribute> monData = mon.getMonitorData(); |
| | | // TODO Check Monitoring Attributes |
| | | } |
| | | |
| | | } |