Integration tests with spring-security and ldap

2019-02-18 06:17发布

问题:

Spring embedded ldap server in unit tests is similar, however no answer was given that suites me.

I can run my integration tests with spring and the embedded ldap server of spring-security without any problems. However, I haven't find a way yet to clear the embedded ldap server and load the ldif again to provide a common test environment.

LdapTestUtils of spring-ldap provides a cleanAndSetup() method. However, this does not work with the suggested version (1.5.5) of apache-ds, as LdifFileLoader now requires a CoreSession instead of the DirContext provided by LdapTestUtils. This causes a

java.lang.NoSuchMethodError:
org.apache.directory.server.protocol.shared.store.LdifFileLoader.<init>(Ljavax/naming/directory/DirContext;Ljava/lang/String;)

I only want a method that clear the embedded ldap server and fills it with the ldif file again (as done on startup). Does anybody have an idea regarding this?

Version: spring 3.1, spring-ldap 1.3, spring-security 3.1, apache-ds 1.5.5

Solution (Thanks to Luke Taylor):

@Inject
private ApplicationContext applicationContext;

@Before
public void reloadLdapDirectory() throws NamingException, IOException{
    ApacheDSContainer apacheDSContainer = (ApacheDSContainer) applicationContext.getBean(BeanIds.EMBEDDED_APACHE_DS);
    LdapTestUtils.clearSubContexts(contextSource, DistinguishedName.EMPTY_PATH);

    ClassPathResource classPathResource = new ClassPathResource("ldap.ldif");

    File tempFile = File.createTempFile("spring_ldap_test", ".ldif");
    try {
        InputStream inputStream = classPathResource.getInputStream();
        IOUtils.copy(inputStream, new FileOutputStream(tempFile));
        LdifFileLoader fileLoader = new LdifFileLoader(apacheDSContainer.getService().getAdminSession(), tempFile.getAbsolutePath());
        fileLoader.execute();
    }
    finally {
        try {
            tempFile.delete();
        }
        catch (Exception e) {
            // Ignore this
        }
    }
}

回答1:

Why not take a look at Spring Security's LDAP integration tests and use those as a guide?

At the moment, these just use an LDAP template to clear out data that each test has created if necessary (for speed), but there is also a commented-out Junit @After method which does reload an LDIF file. The CoreSession is obtained by calling getAdminSession() on the server instance (a DefaultDirectoryService).

If you really have to run the tests using an XML application context, using the <ldap-server /> element, you can use:

getBeanByName(BeanIds.EMBEDDED_APACHE_DS).getService()

to get access to the DefaultDirectoryService instance.