Search code examples
javascopesingletoncdijava-ee-7

How to define a singleton object for a class I didn't write in Java EE?


Let's imagine I want a single not.my.Clock through my application:

public final class Clock {
  ... // business
}

I can write the following:

@Singleton
public class ClockProvider implements Supplier<Clock> {
  private Clock clock;
  @PostConstruct
  void init() {
    clock = ... ;
  }
  @Override
  public Clock get() {
    return clock;
  }
}

@RequestScoped
public class MyBean {
  @Inject ClockProvider clockProvider;
  // Use clockProvider.get()
}

How can I define a singleton object for my whole application instead of a singleton provider, so that I can write the following code? The Java EE 7 tutorial only speaks about singleton session bean, not singleton objects.

@RequestScoped
public class MyBean {
  @Inject Clock clock;
  // Use clock directly: no clock-provider.
}

If I had to write this in Guice, I'd write something like this:

bind(Clock.class).toInstance(...);

Or

@Provides @Singleton Clock provideClock() {
  return ... ;
}

Solution

  • You can use @Produces and @ApplicationScoped annotations on public Clock get() method to produces a Clock singleton :

    @Produces
    @ApplicationScoped
    public Clock get() {
        // your code
    }