Designing a Java library with Spring

Designing a Java library with Spring

How do I initialise the librarys context? I cannot assume that
library users will make use of Spring too, but I can distribute Spring
with the library.

I am writing a library using Spring context as well and I did something like that, assuming your library is called FooLib, has two services called FooService and BarService and a class called SpringContext that configures your spring context through java config:

public final class FooLib {

    private static ApplicationContext applicationContext;

    private FooLib() {
    }

    public static FooService getFooService() {
        return getApplicationContext().getBean(FooService.class);
    }

    public static BarService getBarService() {
        return getApplicationContext().getBean(BarService.class);
    }

    private static ApplicationContext getApplicationContext() {
        if (applicationContext == null) {
            applicationContext = new AnnotationConfigApplicationContext(SpringContext.class);
        }
        return applicationContext;
    }
}

Then a client can use BarService this way:

BarService barService = FooLib.getBarService();

How do I manage my filesystem monitoring thread? Is it good design to
expect the program to instantiate a main class of the library and the
call init or something like that?

You can start your monitoring subsystem statically within Spring context, inside the SpringContext class, for example.

@Configuration
@ComponentScan(basePackages = com.yourgroupid.foolib)
public class SpringContext {

    @Bean
    public MonitoringSystem monitoringSystem() {
        MonitoringSystem monitoringSystem = new MonitoringSystem();
        monitoringSystem.start();
        return monitoringSystem;
    }

}

That should be enough because Spring creates its beans eagerly by default.

Cheers

How do I initialise the librarys context? I cannot assume that library users will make use of Spring too, but I can distribute Spring with the library.

Its up to your library to instantiate spring the way you need it. This is typically done in your interface entrypoint which delegates to a routine using e.g., ClassPathXmlApplicationContext to configure spring. A sample could be

public class SpringContextLoader {
   private static ApplicationContext ctx = null;
   public static void init() {
       if (ctx == null) {
          ctx = ClassPathXmlApplicationContext(classpath:/applicatonContext.xml);
       }
   }
}

How do I manage my filesystem monitoring thread? Is it good design to expect the program to instantiate a main class of the library and the call init or something like that?

In this case you will probably provide a non-daemon thread, e.g., a thread which must be terminated manually for the application to exit cleanly. Hence you should provide start and stop mechanisms. In your case these probably better be called registerEventListener and unregisterAllEventListener (since Im guessing you want to pass filesystem events to the client … ). Another alternative could be to use quartz scheduling with spring.

Designing a Java library with Spring

How do I initialise the librarys context? I cannot assume that library users will make use of Spring too, but I can distribute Spring with the library.

You can use a PropertyPlaceholderConfigurer to read configuration settings from a (possibly external) property file, which can be edited by the users. This way users arent exposed to the details of Spring, not even to XML config files.

How do I manage my filesystem monitoring thread? Is it good design to expect the program to instantiate a main class of the library and the call init or something like that?

I recommend using the Java concurrency framework, specifically a ScheduledExecutorService to run monitoring task(s) at specified intervals. However, you may want to hide this implementation detail from the users of your library, by only exposing some init method to pass in the desired timer interval.

Leave a Reply

Your email address will not be published. Required fields are marked *