tip: to bind dagger singletons to a particular object graph scope, use injects=

 

{note: this blog entry is about dagger 1}

If you want singleton semantics for injected objects, dagger offers two approaches - you can implement a @Singleton-annotated provider method, or you can implement an @Inject-annotated constructor in a @Singleton-annotated class. The latter approach is obviously a little more concise, but it raises one issue, which is that in an application with multiple object graphs, some of which extend others (e.g. an Activity-scope graph that extends an Application-scope graph), dagger will maintain singletons of those @Singleton-annotated classes in each object graph that is requested to inject one.  So if you've got a @Singleton-annotated Foo class, you could end up with one Foo object shared by objects that are injected via the Activity-scope graph, and another Foo object shared by objects injected via the Application-scope graph.

There are two ways to avoid this.  Let's assume you want only one Foo instance and you want it to be bound to the Application-scope graph.  In your Application module declaration, you could (1) add a @Singleton-annotated provider method for Foo, or (2) include Foo.class in the "injects=" part of your @Module annotation.  When I first read about this, I found it a little confusing, as I thought the "injects=" list was just for enumerating the classes that the module injects into, but some experimentation confirmed that specifying classes to inject has the effect of binding their @Inject-annotated constructor to that module (essentially creating an implicit provider), and thus to the object graph created from it.