Dependency Injection with Dagger 2 (Devoxx 2014)

Dependency Injection with Dagger 2 (Devoxx 2014)

Dagger is a fast dependency injector for both Java and Android. Its second major version not only brings new features for parity with other frameworks but continues to push the boundaries of speed.

The concepts covered in this talk apply to both Java targeting the JVM and Android.

Video: https://parleys.com/play/5471cdd1e4b065ebcfa1d557/

E68309f117985270285ade8082f4877d?s=128

Jake Wharton

November 13, 2014
Tweet

Transcript

  1. dependency injection with Dagger 2 Jake Wharton

  2. Dependency Injection flickr.com/photos/sunsetnoir/6984108500

  3. Dependency Injection • No “new”, dependencies come to you flickr.com/photos/sunsetnoir/6984108500

  4. Dependency Injection • First and foremost a pattern

  5. Dependency Injection • First and foremost a pattern • Every

    single app has some form of dependency injection
  6. Dependency Injection • First and foremost a pattern • Every

    single app has some form of dependency injection Tweeter
  7. Dependency Injection • First and foremost a pattern • Every

    single app has some form of dependency injection Twitter API Tweeter
  8. Dependency Injection • First and foremost a pattern • Every

    single app has some form of dependency injection Twitter API Tweeter HTTP Client
  9. public class Tweeter {
 public void tweet(String tweet) {
 TwitterApi

    api = new TwitterApi();
 api.postTweet("JakeWharton", tweet);
 }
 }
  10. public class Tweeter {
 public void tweet(String tweet) {
 TwitterApi

    api = new TwitterApi();
 api.postTweet("JakeWharton", tweet);
 }
 } public class TwitterApi {
 public void postTweet(String user, String tweet) {
 OkHttpClient client = new OkHttpClient();
 Request request = // TODO build POST request...
 client.newCall(request).execute();
 }
 }
  11. public class Tweeter {
 public void tweet(String tweet) {
 TwitterApi

    api = new TwitterApi();
 api.postTweet("JakeWharton", tweet);
 }
 } public class TwitterApi {
 public void postTweet(String user, String tweet) {
 OkHttpClient client = new OkHttpClient();
 Request request = // TODO build POST request...
 client.newCall(request).execute();
 }
 } Tweeter tweeter = new Tweeter();
 tweeter.tweet("Hello, #Devoxx 2014!");
  12. public class TwitterApi {
 public void postTweet(String user, String tweet)

    {
 OkHttpClient client = new OkHttpClient();
 Request request = // TODO build POST request...
 client.newCall(request).execute();
 }
 }
  13. public class TwitterApi {
 private final OkHttpClient client = new

    OkHttpClient();
 
 public void postTweet(String user, String tweet) {
 Request request = // TODO build POST request...
 client.newCall(request).execute();
 }
 }
  14. public class TwitterApi {
 private final OkHttpClient client = new

    OkHttpClient();
 
 public void postTweet(String user, String tweet) {
 Request request = // TODO build POST request...
 client.newCall(request).execute();
 }
 }
  15. public class TwitterApi {
 private final OkHttpClient client;
 
 public

    TwitterApi(OkHttpClient client) {
 this.client = client;
 }
 
 public void postTweet(String user, String tweet) {
 Request request = // TODO build POST request...
 client.newCall(request).execute();
 }
 }
  16. public class TwitterApi {
 private final OkHttpClient client;
 
 public

    TwitterApi(OkHttpClient client) {
 this.client = client;
 }
 
 public void postTweet(String user, String tweet) {
 Request request = // TODO build POST request...
 client.newCall(request).execute();
 }
 }
  17. public class Tweeter {
 public void tweet(String tweet) {
 TwitterApi

    api = new TwitterApi();
 api.postTweet("JakeWharton", tweet);
 } }
  18. public class Tweeter {
 public void tweet(String tweet) {
 TwitterApi

    api = new TwitterApi(new OkHttpClient());
 api.postTweet("JakeWharton", tweet);
 }
 }
  19. public class Tweeter {
 public void tweet(String tweet) {
 TwitterApi

    api = new TwitterApi(new OkHttpClient());
 api.postTweet("JakeWharton", tweet);
 }
 }
  20. public class Tweeter {
 private final TwitterApi api = new

    TwitterApi(new OkHttpClient());
 
 public void tweet(String tweet) {
 api.postTweet("JakeWharton", tweet);
 }
 }
  21. public class Tweeter {
 private final TwitterApi api = new

    TwitterApi(new OkHttpClient());
 
 public void tweet(String tweet) {
 api.postTweet("JakeWharton", tweet);
 }
 }
  22. public class Tweeter {
 private final TwitterApi api = new

    TwitterApi(new OkHttpClient());
 private final String user;
 
 public Tweeter(String user) {
 this.user = user;
 }
 
 public void tweet(String tweet) {
 api.postTweet(user, tweet);
 }
 }
  23. public class Tweeter {
 private final TwitterApi api = new

    TwitterApi(new OkHttpClient());
 private final String user;
 
 public Tweeter(String user) {
 this.user = user;
 }
 
 public void tweet(String tweet) {
 api.postTweet(user, tweet);
 }
 }
  24. Tweeter tweeter = new Tweeter();
 tweeter.tweet("Hello, #Devoxx 2014!");

  25. Tweeter tweeter = new Tweeter("JakeWharton");
 tweeter.tweet("Hello, #Devoxx 2014!");

  26. Tweeter tweeter = new Tweeter("JakeWharton");
 tweeter.tweet("Hello, #Devoxx 2014!");

  27. Tweeter tweeter = new Tweeter("JakeWharton");
 tweeter.tweet("Hello, #Devoxx 2014!"); ! 


    tweeter.tweet("#Hungover #Dagger"); ! 
 tweeter.tweet("Waffles, beer, diamonds, chocolate, and Dagger!"); ! 
 ! tweeter.tweet("Java Posse ain’t got nothing on #Dagger"); ! 
 ! ! tweeter.tweet("Are these the same slides from last year? #meta"); ! 
 ! ! ! tweeter.tweet("I need an injection of beer, amirite? #Dagger");
  28. Tweeter tweeter = new Tweeter("JakeWharton");
 tweeter.tweet("Hello, #Devoxx 2014!"); ! 


    tweeter.tweet("#Hungover #Dagger"); ! 
 tweeter.tweet("Waffles, beer, diamonds, chocolate, and Dagger!"); ! 
 ! tweeter.tweet("Java Posse ain’t got nothing on #Dagger"); ! 
 ! ! tweeter.tweet("Are these the same slides from last year? #meta"); ! 
 ! ! ! tweeter.tweet("I need an injection of beer, amirite? #Dagger"); Timeline timeline = new Timeline("JakeWharton");
 timeline.loadMore(20);
 for (Tweet tweet : timeline.get()) {
 System.out.println(tweet);
 }
  29. public class Timeline {
 private final List<Tweet> cache = new

    ArrayList<>();
 private final TwitterApi api = new TwitterApi(new OkHttpClient());
 private final String user;
 
 public Timeline(String user) {
 this.user = user;
 }
 
 public List<Tweet> get() { /* ... */ }
 public void loadMore(int amount) { /* ... */ }
 }
  30. public class Timeline {
 private final List<Tweet> cache = new

    ArrayList<>();
 private final TwitterApi api;
 private final String user;
 
 public Timeline(TwitterApi api, String user) {
 this.api = api;
 this.user = user;
 }
 
 public List<Tweet> get() { /* ... */ }
 public void loadMore(int amount) { /* ... */ }
 }
  31. public class Timeline {
 private final List<Tweet> cache = new

    ArrayList<>();
 private final TwitterApi api;
 private final String user;
 
 public Timeline(TwitterApi api, String user) {
 this.api = api;
 this.user = user;
 }
 
 public List<Tweet> get() { /* ... */ }
 public void loadMore(int amount) { /* ... */ }
 }
  32. public class Tweeter {
 private final TwitterApi api = new

    TwitterApi(new OkHttpClient());
 private final String user;
 
 public Tweeter(String user) {
 this.user = user;
 }
 
 public void tweet(String tweet) {
 api.postTweet(user, tweet);
 }
 }
  33. public class Tweeter {
 private final TwitterApi api;
 private final

    String user;
 
 public Tweeter(TwitterApi api, String user) {
 this.api = api;
 this.user = user;
 }
 
 public void tweet(String tweet) {
 api.postTweet(user, tweet);
 }
 }
  34. public class Tweeter {
 private final TwitterApi api;
 private final

    String user;
 
 public Tweeter(TwitterApi api, String user) {
 this.api = api;
 this.user = user;
 }
 
 public void tweet(String tweet) {
 api.postTweet(user, tweet);
 }
 }
  35. Tweeter tweeter = new Tweeter("JakeWharton");
 tweeter.tweet("Hello, #Devoxx 2014!");
 
 Timeline

    timeline = new Timeline("JakeWharton");
 timeline.loadMore(20);
 for (Tweet tweet : timeline.get()) {
 System.out.println(tweet);
 }
  36. OkHttpClient client = new OkHttpClient();
 TwitterApi api = new TwitterApi(client);


    String user = "Jake Wharton";
 
 Tweeter tweeter = new Tweeter(api, user);
 tweeter.tweet("Hello, #Devoxx 2014!");
 
 Timeline timeline = new Timeline(api, user);
 timeline.loadMore(20);
 for (Tweet tweet : timeline.get()) {
 System.out.println(tweet);
 }
  37. OkHttpClient client = new OkHttpClient();
 TwitterApi api = new TwitterApi(client);


    String user = "Jake Wharton";
 
 Tweeter tweeter = new Tweeter(api, user);
 tweeter.tweet("Hello, #Devoxx 2014!");
 
 Timeline timeline = new Timeline(api, user);
 timeline.loadMore(20);
 for (Tweet tweet : timeline.get()) {
 System.out.println(tweet);
 }
  38. Dependency Injection • First and foremost a pattern • Every

    single app has some form of dependency injection Twitter API Tweeter HTTP Client
  39. Dependency Injection • First and foremost a pattern • Every

    single app has some form of dependency injection Twitter API Tweeter HTTP Client Tweeter
  40. Dependency Injection Twitter API Tweeter HTTP Client Tweeter • How

    do we avoid the boilerplate that comes with the pattern?
  41. Library Rescue • Spring • Guice • Dagger (v1) •

    PicoContainer • CDI • Others…
  42. Guice Dagger (v1)

  43. Guice

  44. Guice • Developed at Google by Bob Lee, later Jesse

    Wilson, others.
  45. Guice • Developed at Google by Bob Lee, later Jesse

    Wilson, others. • Adopted and maintained by Java Core Libraries team.
  46. Guice • Developed at Google by Bob Lee, later Jesse

    Wilson, others. • Adopted and maintained by Java Core Libraries team. • Powerful, dynamic, well-tested, wide-spread, etc…
  47. Guice • Developed at Google by Bob Lee, later Jesse

    Wilson, others. • Adopted and maintained by Java Core Libraries team. • Powerful, dynamic, well-tested, wide-spread, etc… • Configuration problems occur at runtime.
  48. Guice • Developed at Google by Bob Lee, later Jesse

    Wilson, others. • Adopted and maintained by Java Core Libraries team. • Powerful, dynamic, well-tested, wide-spread, etc… • Configuration problems occur at runtime. • Slow initialization, slow injection, memory concerns.
  49. Dagger (v1)

  50. Dagger (v1) • Developed at Square by Jesse Wilson advised

    by Bob Lee.
  51. Dagger (v1) • Developed at Square by Jesse Wilson advised

    by Bob Lee. • Initially targeted at highly resource constrained environments.
  52. Dagger (v1) • Developed at Square by Jesse Wilson advised

    by Bob Lee. • Initially targeted at highly resource constrained environments. • Static analysis of all dependencies and injection points.
  53. Dagger (v1) • Developed at Square by Jesse Wilson advised

    by Bob Lee. • Initially targeted at highly resource constrained environments. • Static analysis of all dependencies and injection points. • Fail as early as possible (compile-time, not runtime)
  54. Dagger (v1) • Developed at Square by Jesse Wilson advised

    by Bob Lee. • Initially targeted at highly resource constrained environments. • Static analysis of all dependencies and injection points. • Fail as early as possible (compile-time, not runtime) • Eliminate reflection on methods, fields, and annotations.
  55. Dagger (v1)

  56. Dagger (v1) • Wide-spread, successful use in large Android applications.

  57. Dagger (v1) • Wide-spread, successful use in large Android applications.

    • Triggers over-eager class loading on graph creation.
  58. Dagger (v1) • Wide-spread, successful use in large Android applications.

    • Triggers over-eager class loading on graph creation. • FQCN string-based keys in map-like data structure.
  59. Dagger (v1) • Wide-spread, successful use in large Android applications.

    • Triggers over-eager class loading on graph creation. • FQCN string-based keys in map-like data structure. • Lack of full static scope analysis and scope annotations.
  60. Dagger (v1) • Wide-spread, successful use in large Android applications.

    • Triggers over-eager class loading on graph creation. • FQCN string-based keys in map-like data structure. • Lack of full static scope analysis and scope annotations. • Still uses reflection to load generated classes.
  61. Dagger (v2)

  62. Dagger (v2) • Proposed and implemented by Java Core Libraries

    team.
  63. Dagger (v2) • Proposed and implemented by Java Core Libraries

    team. • Eliminate runtime library and generated code overhead.
  64. Dagger (v2) • Proposed and implemented by Java Core Libraries

    team. • Eliminate runtime library and generated code overhead. • Shift remaining runtime analysis to compile time.
  65. Dagger (v2) • Proposed and implemented by Java Core Libraries

    team. • Eliminate runtime library and generated code overhead. • Shift remaining runtime analysis to compile time. • Scoping with annotations and associated static analysis.
  66. Dagger API

  67. Dagger API • @Module + @Provides: mechanism for providing dependencies.

  68. Dagger API • @Module + @Provides: mechanism for providing dependencies.

    • @Inject: mechanism for requesting dependencies.
  69. Dagger API • @Module + @Provides: mechanism for providing dependencies.

    • @Inject: mechanism for requesting dependencies. • @Component: bridge between modules and injections
  70. Dagger API • @Module + @Provides: mechanism for providing dependencies.

    • @Inject: mechanism for requesting dependencies. • @Component: bridge between modules and injections • Plus some other sugar, magic, and conventions.
  71. Providing Dependencies

  72. Providing Dependencies • Modules are classes whose methods provide dependencies.

  73. Providing Dependencies • Modules are classes whose methods provide dependencies.

    • @Module on the class.
  74. Providing Dependencies • Modules are classes whose methods provide dependencies.

    • @Module on the class. • @Provides (and friends) on each method.
  75. 
 public class NetworkModule {
 
 OkHttpClient provideOkHttpClient() {
 return

    new OkHttpClient();
 }
 
 
 TwitterApi provideTwitterApi(OkHttpClient client) {
 return new TwitterApi(client);
 }
 }
  76. 
 public class NetworkModule {
 
 OkHttpClient provideOkHttpClient() {
 return

    new OkHttpClient();
 }
 
 
 TwitterApi provideTwitterApi(OkHttpClient client) {
 return new TwitterApi(client);
 }
 } @Module
  77. 
 public class NetworkModule {
 
 OkHttpClient provideOkHttpClient() {
 return

    new OkHttpClient();
 }
 
 
 TwitterApi provideTwitterApi(OkHttpClient client) {
 return new TwitterApi(client);
 }
 } @Module ! ! @Provides ! ! ! ! ! ! ! @Provides
  78. 
 public class NetworkModule {
 
 OkHttpClient provideOkHttpClient() {
 return

    new OkHttpClient();
 }
 
 
 TwitterApi provideTwitterApi(OkHttpClient client) {
 return new TwitterApi(client);
 }
 } @Module ! ! @Provides ! ! ! ! ! ! ! @Provides ! ! @Singleton ! ! ! ! ! ! ! @Singleton
  79. Providing Dependencies

  80. Providing Dependencies NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi

  81. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi

  82. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi

  83. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterApi provideTwitterApi(OkHttpClient client) {


    return new TwitterApi(client);
 }
  84. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi

  85. Providing Dependencies • Modules are classes whose methods provide dependencies.

    • @Module on the class. • @Provides (and friends) on each method.
  86. Providing Dependencies • Modules are classes whose methods provide dependencies.

    • @Module on the class. • @Provides (and friends) on each method. ! ! ! • Designed to be partitioned and composed together.
  87. 
 public class TwitterModule {
 
 
 
 
 


    
 
 
 
 
 
 
 
 
 
 }
  88. 
 public class TwitterModule {
 
 
 
 
 


    
 
 
 
 
 
 
 
 
 
 } @Module
  89. 
 public class TwitterModule {
 
 
 
 
 


    
 
 
 
 
 
 
 
 
 
 } 
 
 private final String user;
 
 public TwitterModule(String user) {
 this.user = user;
 } @Module
  90. 
 public class TwitterModule {
 
 
 
 
 


    
 
 
 
 
 
 
 
 
 
 } 
 
 private final String user;
 
 public TwitterModule(String user) {
 this.user = user;
 } 
 public class TwitterModule {
 
 
 
 
 
 
 @Provides @Singleton
 Tweeter provideTweeter(TwitterApi api) {
 return new Tweeter(api, user);
 } @Module
  91. 
 public class TwitterModule {
 
 
 
 
 


    
 
 
 
 
 
 
 
 
 
 } 
 
 private final String user;
 
 public TwitterModule(String user) {
 this.user = user;
 } 
 public class TwitterModule {
 
 
 
 
 
 
 @Provides @Singleton
 Tweeter provideTweeter(TwitterApi api) {
 return new Tweeter(api, user);
 } 
 
 
 
 
 
 
 
 
 
 
 
 
 @Provides @Singleton
 Timeline provideTimeline(TwitterApi api) {
 return new Timeline(api, user);
 } @Module
  92. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi

  93. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline

  94. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

  95. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

  96. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter
  97. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter
  98. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterModule#provideTweeter
  99. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterModule#provideTweeter
  100. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterModule#provideTweeter TwitterApi
  101. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterModule#provideTweeter TwitterApi
  102. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterModule#provideTweeter TwitterApi NetworkModule#provideTwitterApi
  103. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterModule#provideTweeter TwitterApi NetworkModule#provideTwitterApi
  104. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterModule#provideTweeter TwitterApi NetworkModule#provideTwitterApi OkHttpClient
  105. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterModule#provideTweeter TwitterApi NetworkModule#provideTwitterApi OkHttpClient
  106. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterModule#provideTweeter TwitterApi NetworkModule#provideTwitterApi OkHttpClient NetworkModule#provideOkHttpClient
  107. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterModule#provideTweeter TwitterApi NetworkModule#provideTwitterApi OkHttpClient NetworkModule#provideOkHttpClient NetworkModule#provideOkHttpClient
  108. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterModule#provideTweeter TwitterApi NetworkModule#provideTwitterApi OkHttpClient NetworkModule#provideOkHttpClient OkHttpClient
  109. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterModule#provideTweeter TwitterApi NetworkModule#provideTwitterApi OkHttpClient OkHttpClient
  110. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterModule#provideTweeter TwitterApi NetworkModule#provideTwitterApi OkHttpClient OkHttpClient NetworkModule#provideTwitterApi
  111. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterModule#provideTweeter TwitterApi NetworkModule#provideTwitterApi OkHttpClient OkHttpClient NetworkModule#provideTwitterApi TwitterApi
  112. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterModule#provideTweeter TwitterApi OkHttpClient OkHttpClient TwitterApi
  113. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterModule#provideTweeter TwitterApi OkHttpClient OkHttpClient TwitterApi TwitterModule#provideTweeter
  114. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterApi OkHttpClient OkHttpClient TwitterApi TwitterModule#provideTweeter Tweeter
  115. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterApi OkHttpClient OkHttpClient TwitterApi Tweeter
  116. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterApi OkHttpClient OkHttpClient TwitterApi Tweeter
  117. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Tweeter TwitterApi OkHttpClient OkHttpClient TwitterApi Tweeter
  118. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Timeline
  119. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Timeline TwitterModule#provideTimeline
  120. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Timeline TwitterModule#provideTimeline
  121. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Timeline TwitterModule#provideTimeline TwitterModule#provideTimeline
  122. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Timeline TwitterModule#provideTimeline Timeline
  123. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Timeline Timeline
  124. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Timeline Timeline
  125. Providing Dependencies OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter Timeline

    Timeline Timeline
  126. Requesting Dependencies

  127. Requesting Dependencies • @Inject annotation required.

  128. Requesting Dependencies • @Inject annotation required. • Constructor, field, and

    method injection.
  129. Constructor Injection

  130. Constructor Injection • @Inject on a single constructor.

  131. Constructor Injection • @Inject on a single constructor. • Constructor

    parameters are dependencies.
  132. Constructor Injection • @Inject on a single constructor. • Constructor

    parameters are dependencies. • Dependencies can be stored in private and final fields.
  133. public class TwitterApplication {
 private final Tweeter tweeter;
 private final

    Timeline timeline;
 
 @Inject
 public TwitterApplication(Tweeter tweeter, Timeline timeline) {
 this.tweeter = tweeter;
 this.timeline = timeline;
 }
 
 // ...
 }
  134. Constructor Injection • @Inject on a single constructor. • Constructor

    parameters are dependencies. • Dependencies can be stored in private and final fields.
  135. Constructor Injection • @Inject on a single constructor. • Constructor

    parameters are dependencies. • Dependencies can be stored in private and final fields. • Implicitly made available for downstream injection.
  136. @Module
 public class NetworkModule {
 @Provides @Singleton
 OkHttpClient provideOkHttpClient() {


    return new OkHttpClient();
 }
 
 @Provides @Singleton
 TwitterApi provideTwitterApi(OkHttpClient client) {
 return new TwitterApi(client);
 }
 }
  137. @Module
 public class NetworkModule {
 @Provides @Singleton
 OkHttpClient provideOkHttpClient() {


    return new OkHttpClient();
 }
 
 @Provides @Singleton
 TwitterApi provideTwitterApi(OkHttpClient client) {
 return new TwitterApi(client);
 }
 } 
 
 
 
 
 
 
 @Provides @Singleton
 
 
 
 
 
 
 
 
 
 
 
 TwitterApi provideTwitterApi(OkHttpClient client) {
 
 
 
 
 
 
 
 
 
 
 
 return new TwitterApi(client);
 
 
 
 
 
 
 
 
 
 
 
 }
 }
  138. public class TwitterApi {
 private final OkHttpClient client;
 
 


    
 public TwitterApi(OkHttpClient client) {
 this.client = client;
 }
 
 public void postTweet(String user, String tweet) {
 Request request = // TODO build POST request ...
 client.newCall(request).execute();
 }
 }
  139. public class TwitterApi {
 private final OkHttpClient client;
 
 


    
 public TwitterApi(OkHttpClient client) {
 this.client = client;
 }
 
 public void postTweet(String user, String tweet) {
 Request request = // TODO build POST request ...
 client.newCall(request).execute();
 }
 } 
 
 
 @Inject
  140. public class TwitterApi {
 private final OkHttpClient client;
 
 


    
 public TwitterApi(OkHttpClient client) {
 this.client = client;
 }
 
 public void postTweet(String user, String tweet) {
 Request request = // TODO build POST request ...
 client.newCall(request).execute();
 }
 } 
 
 
 @Inject @Singleton
  141. Method Injection

  142. Method Injection • @Inject on methods.

  143. Method Injection • @Inject on methods. • Method parameters are

    dependencies.
  144. Method Injection • @Inject on methods. • Method parameters are

    dependencies. • Injection happens after object is fully instantiated.
  145. Method Injection • @Inject on methods. • Method parameters are

    dependencies. • Injection happens after object is fully instantiated. • Only one valid use case: passing ‘this’ to a dependency.
  146. public class TwitterApplication {
 private final Tweeter tweeter;
 private final

    Timeline timeline;
 
 @Inject
 public TwitterApplication(Tweeter tweeter, Timeline timeline) {
 this.tweeter = tweeter;
 this.timeline = timeline;
 }
 
 
 
 
 }
  147. public class TwitterApplication {
 private final Tweeter tweeter;
 private final

    Timeline timeline;
 
 @Inject
 public TwitterApplication(Tweeter tweeter, Timeline timeline) {
 this.tweeter = tweeter;
 this.timeline = timeline;
 }
 
 
 
 
 } public class TwitterApplication {
 private final Tweeter tweeter;
 private final Timeline timeline;
 
 @Inject
 public TwitterApplication(Tweeter tweeter, Timeline timeline) {
 this.tweeter = tweeter;
 this.timeline = timeline;
 }
 
 
 
 
 } ! ! ! ! ! ! ! ! ! ! @Inject
 public void enableStreaming(Streaming streaming) {
 streaming.register(this);
 }
  148. public class TwitterApplication {
 private final Tweeter tweeter;
 private final

    Timeline timeline;
 
 @Inject
 public TwitterApplication(Tweeter tweeter, Timeline timeline) {
 this.tweeter = tweeter;
 this.timeline = timeline;
 }
 
 
 
 
 } ! ! ! ! ! ! ! ! ! ! @Inject
 public void enableStreaming(Streaming streaming) {
 streaming.register(this);
 }
  149. Field Injection

  150. Field Injection • @Inject on fields for dependencies.

  151. Field Injection • @Inject on fields for dependencies. • Field

    may not be private or final.
  152. public class TwitterApplication {
 @Inject Tweeter tweeter;
 @Inject Timeline timeline;


    
 // ...
 }
  153. public class TwitterActivity extends Activity {
 @Inject Tweeter tweeter;
 @Inject

    Timeline timeline;
 
 // ...
 }
  154. public class TwitterProcessor extends AbstractProcessor {
 @Inject Tweeter tweeter;
 @Inject

    Timeline timeline;
 
 // ...
 }
  155. Field Injection • @Inject on fields for dependencies. • Field

    may not be private or final.
  156. Field Injection • @Inject on fields for dependencies. • Field

    may not be private or final. • Injection happens after the object is fully instantiated.
  157. Field Injection • @Inject on fields for dependencies. • Field

    may not be private or final. • Injection happens after the object is fully instantiated. • Object is usually responsible for or aware of injection.
  158. Components

  159. Components • Bridge between modules and injection.

  160. Components • Bridge between modules and injection. • The injector.

  161. @Component ! public interface TwitterComponent { 
 
 }

  162. @Component ! public interface TwitterComponent { 
 
 } (modules

    = { NetworkModule.class,
 TwitterModule.class,
 })
  163. @Component ! public interface TwitterComponent { 
 
 } (modules

    = { NetworkModule.class,
 TwitterModule.class,
 }) @Singleton
  164. @Component 
 
 
 
 
 Tweeter tweeter();
 Timeline timeline();

    ! public interface TwitterComponent { 
 
 } (modules = { NetworkModule.class,
 TwitterModule.class,
 }) @Singleton
  165. TwitterComponent component = Dagger_TwitterComponent.builder()
 .networkModule(new NetworkModule())
 .twitterModule(new TwitterModule("JakeWharton"))
 .build();

  166. TwitterComponent component = Dagger_TwitterComponent.builder()
 .networkModule(new NetworkModule())
 .twitterModule(new TwitterModule("JakeWharton"))
 .build(); !

    ! ! ! ! ! Timeline timeline = component.timeline(); ! ! ! ! 
 Tweeter tweeter = component.tweeter();
  167. TwitterComponent component = Dagger_TwitterComponent.builder() 
 
 .twitterModule(new TwitterModule("JakeWharton"))
 .build(); !

    Tweeter tweeter = component.tweeter(); 
 .networkModule(new NetworkModule()) 
 .networkModule(new NetworkModule()) 
 
 
 ! ! Timeline timeline = component.timeline();
  168. TwitterComponent component = Dagger_TwitterComponent.builder() 
 
 .twitterModule(new TwitterModule("JakeWharton"))
 .build(); !

    Tweeter tweeter = component.tweeter(); 
 
 
 ! ! Timeline timeline = component.timeline();
  169. TwitterComponent component = Dagger_TwitterComponent.builder() 
 
 .twitterModule(new TwitterModule("JakeWharton"))
 .build(); !

    Tweeter tweeter = component.tweeter(); tweeter.tweet("Hello, #Devoxx 2014!"); timeline.loadMore(20);
 for (Tweet tweet : timeline.get()) {
 System.out.println(tweet);
 } 
 
 
 ! ! Timeline timeline = component.timeline();
  170. public class TwitterApplication implements Runnable {
 private final Tweeter tweeter;


    private final Timeline timeline;
 
 @Inject
 public TwitterApplication(Tweeter tweeter, Timeline timeline) {
 this.tweeter = tweeter;
 this.timeline = timeline;
 }
 
 @Override public void run() {
 tweeter.tweet("Hello #Devoxx 2014!");
 
 timeline.loadMore(20);
 for (Tweet tweet : timeline.get()) {
 System.out.println(tweet);
 }
 }
 }
  171. @Singleton @Component(modules = {
 NetworkModule.class,
 TwitterModule.class,
 })
 interface TwitterComponent {


    TwitterApplication app();
 }
  172. @Singleton @Component(modules = {
 NetworkModule.class,
 TwitterModule.class,
 })
 interface TwitterComponent {


    TwitterApplication app();
 } TwitterComponent component = Dagger_TwitterComponent.builder()
 .twitterModule(new TwitterModule("JakeWharton"))
 .build();
 component.app().run();
  173. public class TwitterApplication implements Runnable {
 @Inject Tweeter tweeter;
 @Inject

    Timeline timeline;
 
 @Override public void run() {
 tweeter.tweet("Hello #Devoxx 2014!");
 
 timeline.loadMore(20);
 for (Tweet tweet : timeline.get()) {
 System.out.println(tweet);
 }
 } }
  174. @Singleton @Component(modules = {
 NetworkModule.class,
 TwitterModule.class,
 })
 interface TwitterComponent {


    void injectApp(TwitterApplication app); }
  175. @Singleton @Component(modules = {
 NetworkModule.class,
 TwitterModule.class,
 })
 interface TwitterComponent {


    void injectApp(TwitterApplication app); } TwitterComponent component = Dagger_TwitterComponent.builder()
 .twitterModule(new TwitterModule("JakeWharton"))
 .build();
  176. @Singleton @Component(modules = {
 NetworkModule.class,
 TwitterModule.class,
 })
 interface TwitterComponent {


    void injectApp(TwitterApplication app); } TwitterComponent component = Dagger_TwitterComponent.builder()
 .twitterModule(new TwitterModule("JakeWharton"))
 .build(); TwitterApplication app = new TwitterApplication();
 component.injectApp(app);
 app.run();
  177. @Singleton @Component(modules = {
 NetworkModule.class,
 TwitterModule.class,
 })
 interface TwitterComponent {


    void injectActivity(TwitterActivity activity); } TwitterComponent component = Dagger_TwitterComponent.builder()
 .twitterModule(new TwitterModule("JakeWharton"))
 .build(); TwitterActivity activity = // Android creates instance...
 component.injectActivity(activity); @Singleton @Component(modules = {
 NetworkModule.class,
 TwitterModule.class,
 })
 interface TwitterComponent {
 void injectActivity(TwitterActivity activity); } TwitterComponent component = Dagger_TwitterComponent.builder()
 .twitterModule(new TwitterModule("JakeWharton"))
 .build();
  178. @Singleton @Component(modules = {
 NetworkModule.class,
 TwitterModule.class,
 })
 interface TwitterComponent {


    void injectActivity(TwitterActivity activity); } TwitterComponent component = Dagger_TwitterComponent.builder()
 .twitterModule(new TwitterModule("JakeWharton"))
 .build(); TwitterActivity activity = // Android creates instance...
 component.injectActivity(activity);
  179. @Singleton @Component(modules = {
 NetworkModule.class,
 TwitterModule.class,
 })
 interface TwitterComponent {


    void injectProcessor(TwitterProcessor processor); } TwitterComponent component = Dagger_TwitterComponent.builder()
 .twitterModule(new TwitterModule("JakeWharton"))
 .build(); TwitterProcessor processor = // ServiceLoader creates instance...
 component.injectProcessor(processor); @Singleton @Component(modules = {
 NetworkModule.class,
 TwitterModule.class,
 })
 interface TwitterComponent {
 void injectProcessor(TwitterProcessor processor); } TwitterComponent component = Dagger_TwitterComponent.builder()
 .twitterModule(new TwitterModule("JakeWharton"))
 .build();
  180. @Singleton @Component(modules = {
 NetworkModule.class,
 TwitterModule.class,
 })
 interface TwitterComponent {


    void injectProcessor(TwitterProcessor processor); } TwitterComponent component = Dagger_TwitterComponent.builder()
 .twitterModule(new TwitterModule("JakeWharton"))
 .build(); TwitterProcessor processor = // ServiceLoader creates instance...
 component.injectProcessor(processor);
  181. @Singleton @Component(modules = {
 NetworkModule.class,
 TwitterModule.class,
 })
 interface TwitterComponent {


    TwitterApplication injectApp(TwitterApplication app); } TwitterComponent component = Dagger_TwitterComponent.builder()
 .twitterModule(new TwitterModule("JakeWharton"))
 .build(); TwitterApplication app = new TwitterApplication();
 component.injectApp(app).run(); @Singleton @Component(modules = {
 NetworkModule.class,
 TwitterModule.class,
 })
 interface TwitterComponent {
 TwitterApplication injectApp(TwitterApplication app); } TwitterComponent component = Dagger_TwitterComponent.builder()
 .twitterModule(new TwitterModule("JakeWharton"))
 .build();
  182. @Singleton @Component(modules = {
 NetworkModule.class,
 TwitterModule.class,
 })
 interface TwitterComponent {


    TwitterApplication injectApp(TwitterApplication app); } TwitterComponent component = Dagger_TwitterComponent.builder()
 .twitterModule(new TwitterModule("JakeWharton"))
 .build(); TwitterApplication app = new TwitterApplication();
 component.injectApp(app).run();
  183. Components • Bridge between modules and injection. • The injector.

  184. Components • Bridge between modules and injection. • The injector.

    • Implementation of scopes.
  185. @Singleton
 @Component(modules = NetworkModule.class)
 public interface ApiComponent { 
 


    
 }
  186. @Singleton
 @Component(modules = NetworkModule.class)
 public interface ApiComponent { 
 


    
 } @Component( 
 modules = TwitterModule.class
 )
 public interface TwitterComponent {
 TwitterApplication app();
 }
  187. @Singleton
 @Component(modules = NetworkModule.class)
 public interface ApiComponent { 
 


    
 } @Component( 
 dependencies = ApiComponent.class, 
 modules = TwitterModule.class
 )
 public interface TwitterComponent {
 TwitterApplication app();
 }
  188. @Singleton
 @Component(modules = NetworkModule.class)
 public interface ApiComponent { 
 


    
 } 
 
 
 TwitterApi api();
 @Component( 
 dependencies = ApiComponent.class, 
 modules = TwitterModule.class
 )
 public interface TwitterComponent {
 TwitterApplication app();
 }
  189. @Singleton
 @Component(modules = NetworkModule.class)
 public interface ApiComponent { TwitterApi api();

    } @Component(
 dependencies = ApiComponent.class, modules = TwitterModule.class
 )
 public interface TwitterComponent {
 TwitterApplication app();
 } @Singleton
  190. @Singleton
 @Component(modules = NetworkModule.class)
 public interface ApiComponent { TwitterApi api();

    } @Component(
 dependencies = ApiComponent.class, modules = TwitterModule.class
 )
 public interface TwitterComponent {
 TwitterApplication app();
 } @Singleton
  191. @Singleton
 @Component(modules = NetworkModule.class)
 public interface ApiComponent { TwitterApi api();

    } @Component(
 dependencies = ApiComponent.class, modules = TwitterModule.class
 )
 public interface TwitterComponent {
 TwitterApplication app();
 }
  192. @Module
 public class TwitterModule {
 private final String user;
 


    public TwitterModule(String user) {
 this.user = user;
 }
 
 @Provides @Singleton
 Tweeter provideTweeter(TwitterApi api) {
 return new Tweeter(api, user);
 }
 
 @Provides @Singleton
 Timeline provideTimeline(TwitterApi api) {
 return new Timeline(api, user);
 }
 }
  193. @Module
 public class TwitterModule {
 private final String user;
 


    public TwitterModule(String user) {
 this.user = user;
 }
 
 @Provides @Singleton
 Tweeter provideTweeter(TwitterApi api) {
 return new Tweeter(api, user);
 }
 
 @Provides @Singleton
 Timeline provideTimeline(TwitterApi api) {
 return new Timeline(api, user);
 }
 }
  194. @Module
 public class TwitterModule {
 private final String user;
 


    public TwitterModule(String user) {
 this.user = user;
 }
 
 @Provides
 Tweeter provideTweeter(TwitterApi api) {
 return new Tweeter(api, user);
 }
 
 @Provides
 Timeline provideTimeline(TwitterApi api) {
 return new Timeline(api, user);
 }
 }
  195. ApiComponent apiComponent = Dagger_ApiComponent. builder().build();

  196. ApiComponent apiComponent = Dagger_ApiComponent. create(); ApiComponent apiComponent = Dagger_ApiComponent.

  197. ApiComponent apiComponent = Dagger_ApiComponent. create();

  198. ApiComponent apiComponent = Dagger_ApiComponent. create(); TwitterComponent twitterComponent = Dagger_TwitterComponent.builder()
 .apiComponent(apiComponent)


    .twitterModule(new TwitterModule("Jake Wharton"))
 .build();
  199. ApiComponent apiComponent = Dagger_ApiComponent. create(); TwitterComponent twitterComponent = Dagger_TwitterComponent.builder()
 .apiComponent(apiComponent)


    .twitterModule(new TwitterModule("Jake Wharton"))
 .build(); component.app().run();
  200. Scope Annotations

  201. Scope Annotations • Only create a single instance.

  202. Scope Annotations • Only create a single instance. • @Singleton

    is the “largest” scope.
  203. Scope Annotations • Only create a single instance. • @Singleton

    is the “largest” scope. • Custom annotations for semantic clarity, shorter lifetime.
  204. public @interface User {
 } Scope Annotations • Only create

    a single instance. • @Singleton is the “largest” scope. • Custom annotations for semantic clarity, shorter lifetime.
  205. public @interface User {
 } @Scope Scope Annotations • Only

    create a single instance. • @Singleton is the “largest” scope. • Custom annotations for semantic clarity, shorter lifetime.
  206. @Module
 public class TwitterModule {
 private final String user;
 


    public TwitterModule(String user) {
 this.user = user;
 }
 
 @Provides
 Tweeter provideTweeter(TwitterApi api) {
 return new Tweeter(api, user);
 }
 
 @Provides
 Timeline provideTimeline(TwitterApi api) {
 return new Timeline(api, user);
 }
 }
  207. @Module
 public class TwitterModule {
 private final String user;
 


    public TwitterModule(String user) {
 this.user = user;
 }
 
 @Provides
 Tweeter provideTweeter(TwitterApi api) {
 return new Tweeter(api, user);
 }
 
 @Provides
 Timeline provideTimeline(TwitterApi api) {
 return new Timeline(api, user);
 }
 } @Module
 public class TwitterModule {
 private final String user;
 
 public TwitterModule(String user) {
 this.user = user;
 }
 
 @Provides @User
 Tweeter provideTweeter(TwitterApi api) {
 return new Tweeter(api, user);
 }
 
 @Provides @User
 Timeline provideTimeline(TwitterApi api) {
 return new Timeline(api, user);
 }
 }
  208. @Component(
 dependencies = ApiComponent.class, modules = TwitterModule.class
 )
 public interface

    TwitterComponent {
 TwitterApplication app();
 }
  209. @Component(
 dependencies = ApiComponent.class, modules = TwitterModule.class
 )
 public interface

    TwitterComponent {
 TwitterApplication app();
 } @User
  210. OkHttpClient TwitterApi NetworkModule

  211. OkHttpClient TwitterApi NetworkModule ApiComponent

  212. OkHttpClient TwitterApi NetworkModule ApiComponent

  213. OkHttpClient TwitterApi NetworkModule ApiComponent TwitterApi

  214. OkHttpClient TwitterApi NetworkModule ApiComponent TwitterApi

  215. OkHttpClient TwitterApi NetworkModule ApiComponent TwitterApi Tweeter Timeline TwitterModule

  216. OkHttpClient TwitterApi NetworkModule ApiComponent TwitterApi Tweeter Timeline TwitterModule TwitterComponent

  217. OkHttpClient TwitterApi NetworkModule ApiComponent TwitterApi Tweeter Timeline TwitterModule TwitterComponent

  218. OkHttpClient TwitterApi NetworkModule ApiComponent TwitterApi Tweeter Timeline TwitterModule TwitterComponent TwitterApp

  219. OkHttpClient TwitterApi NetworkModule ApiComponent TwitterApi Tweeter Timeline TwitterModule TwitterComponent TwitterApp

  220. OkHttpClient TwitterApi NetworkModule ApiComponent TwitterApi Tweeter Timeline TwitterModule TwitterComponent TwitterApp

  221. OkHttpClient TwitterApi NetworkModule ApiComponent TwitterApi

  222. OkHttpClient TwitterApi NetworkModule ApiComponent TwitterApi Tweeter Timeline TwitterModule TwitterComponent TwitterApp

  223. Under The Hood

  224. Under The Hood OkHttpClient TwitterApi NetworkModule#provideOkHttpClient NetworkModule#provideTwitterApi TwitterModule#provideTweeter TwitterModule#provideTimeline Tweeter

    Timeline
  225. @Module
 public class NetworkModule {
 @Provides @Singleton
 OkHttpClient provideOkHttpClient() {


    return new OkHttpClient();
 }
 
 @Provides @Singleton
 TwitterApi provideTwitterApi(OkHttpClient client) {
 return new TwitterApi(client);
 }
 }
  226. public class NetworkModule {
 OkHttpClient provideOkHttpClient() {} TwitterApi provideTwitterApi(OkHttpClient) {}


    } public final class NetworkModule_ProvideOkHttpClientFactory implements Factory<OkHttpClient> { 
 private final NetworkModule module;
 
 public NetworkModule_ProvideOkHttpClientFactory(NetworkModule module) { 
 this.module = module;
 }
 
 @Override
 public OkHttpClient get() { 
 return module.provideOkHttpClient();
 }
 }
  227. public class NetworkModule {
 OkHttpClient provideOkHttpClient() {} TwitterApi provideTwitterApi(OkHttpClient) {}


    } public final class NetworkModule_ProvideOkHttpClientFactory implements Factory<OkHttpClient> { 
 private final NetworkModule module;
 
 public NetworkModule_ProvideOkHttpClientFactory(NetworkModule module) { 
 this.module = module;
 }
 
 @Override
 public OkHttpClient get() { 
 return module.provideOkHttpClient();
 }
 }
  228. public class NetworkModule {
 OkHttpClient provideOkHttpClient() {} TwitterApi provideTwitterApi(OkHttpClient) {}


    } public final class NetworkModule_ProvideOkHttpClientFactory implements Factory<OkHttpClient> { 
 private final NetworkModule module;
 
 public NetworkModule_ProvideOkHttpClientFactory(NetworkModule module) { 
 this.module = module;
 }
 
 @Override
 public OkHttpClient get() { 
 return module.provideOkHttpClient();
 }
 }
  229. public class NetworkModule {
 OkHttpClient provideOkHttpClient() {} TwitterApi provideTwitterApi(OkHttpClient) {}


    } public final class NetworkModule_ProvideOkHttpClientFactory implements Factory<OkHttpClient> { 
 private final NetworkModule module;
 
 public NetworkModule_ProvideOkHttpClientFactory(NetworkModule module) {
 this.module = module;
 }
 
 @Override
 public OkHttpClient get() { 
 return module.provideOkHttpClient();
 }
 }
  230. public class NetworkModule {
 OkHttpClient provideOkHttpClient() {} TwitterApi provideTwitterApi(OkHttpClient) {}


    } public final class NetworkModule_ProvideOkHttpClientFactory {
 public OkHttpClient get() { 
 return module.provideOkHttpClient();
 }
 } public final class NetworkModule_ProvideTwitterApiFactory implements Factory<TwitterApi> { 
 private final NetworkModule module;
 private final Provider<OkHttpClient> clientProvider;
 
 public NetworkModule_ProvideTwitterApiFactory( NetworkModule module, Provider<OkHttpClient> clientProvider) {
 this.module = module;
 this.clientProvider = clientProvider;
 }
 
 @Override
 public TwitterApi get() {
 return module.provideTwitterApi(clientProvider.get());
 }
 }
  231. public class NetworkModule {
 OkHttpClient provideOkHttpClient() {} TwitterApi provideTwitterApi(OkHttpClient) {}


    } public final class NetworkModule_ProvideOkHttpClientFactory {
 public OkHttpClient get() { 
 return module.provideOkHttpClient();
 }
 } public final class NetworkModule_ProvideTwitterApiFactory implements Factory<TwitterApi> { 
 private final NetworkModule module;
 private final Provider<OkHttpClient> clientProvider;
 
 public NetworkModule_ProvideTwitterApiFactory( NetworkModule module, Provider<OkHttpClient> clientProvider) {
 this.module = module;
 this.clientProvider = clientProvider;
 }
 
 @Override
 public TwitterApi get() {
 return module.provideTwitterApi(clientProvider.get());
 }
 }
  232. public class NetworkModule {
 OkHttpClient provideOkHttpClient() {} TwitterApi provideTwitterApi(OkHttpClient) {}


    } public final class NetworkModule_ProvideOkHttpClientFactory {
 public OkHttpClient get() { 
 return module.provideOkHttpClient();
 }
 } public final class NetworkModule_ProvideTwitterApiFactory implements Factory<TwitterApi> { 
 private final NetworkModule module;
 private final Provider<OkHttpClient> clientProvider;
 
 public NetworkModule_ProvideTwitterApiFactory( NetworkModule module, Provider<OkHttpClient> clientProvider) {
 this.module = module;
 this.clientProvider = clientProvider;
 }
 
 @Override
 public TwitterApi get() {
 return module.provideTwitterApi(clientProvider.get());
 }
 }
  233. @Singleton
 @Component(modules = NetworkModule.class)
 interface ApiComponent {
 TwitterApi api();
 }

  234. interface ApiComponent {
 TwitterApi api();
 } public final class Dagger_ApiComponent

    implements ApiComponent {
 // ... 
 public static final class Builder {
 private NetworkModule networkModule;
 
 public ApiComponent build() {
 if (networkModule == null) networkModule = new NetworkModule();
 return new Dagger_ApiComponent(this);
 }
 
 public Builder networkModule(NetworkModule networkModule) {
 if (networkModule == null) throw new NullPointerException();
 this.networkModule = networkModule;
 return this;
 }
 }
 }
  235. interface ApiComponent {
 TwitterApi api();
 } public final class Dagger_ApiComponent

    implements ApiComponent {
 // ... 
 public static final class Builder {
 private NetworkModule networkModule;
 
 public ApiComponent build() {
 if (networkModule == null) networkModule = new NetworkModule();
 return new Dagger_ApiComponent(this);
 }
 
 public Builder networkModule(NetworkModule networkModule) {
 if (networkModule == null) throw new NullPointerException();
 this.networkModule = networkModule;
 return this;
 }
 }
 }
  236. interface ApiComponent {
 TwitterApi api();
 } public final class Dagger_ApiComponent

    implements ApiComponent {
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 }
  237. interface ApiComponent {
 TwitterApi api();
 } public final class Dagger_ApiComponent

    implements ApiComponent {
 private Provider<OkHttpClient> provideOkHttpClientProvider;
 private Provider<TwitterApi> provideTwitterApiProvider;
 
 private Dagger_ApiComponent(Builder builder) {
 NetworkModule networkModule = builder.networkModule;
 provideOkHttpClientProvider = ScopedProvider.create( new NetworkModule_ProvideOkHttpClientFactory(networkModule));
 provideTwitterApiProvider = ScopedProvider.create( new NetworkModule_ProvideTwitterApiFactory(networkModule, provideOkHttpClientProvider));
 }
 
 @Override
 public TwitterApi api() {
 return provideTwitterApiProvider.get();
 }
  238. interface ApiComponent {
 TwitterApi api();
 } public final class Dagger_ApiComponent

    implements ApiComponent {
 private Provider<OkHttpClient> provideOkHttpClientProvider;
 private Provider<TwitterApi> provideTwitterApiProvider;
 
 private Dagger_ApiComponent(Builder builder) {
 NetworkModule networkModule = builder.networkModule;
 provideOkHttpClientProvider = ScopedProvider.create( new NetworkModule_ProvideOkHttpClientFactory(networkModule));
 provideTwitterApiProvider = ScopedProvider.create( new NetworkModule_ProvideTwitterApiFactory(networkModule, provideOkHttpClientProvider));
 }
 
 @Override
 public TwitterApi api() {
 return provideTwitterApiProvider.get();
 }
  239. interface ApiComponent {
 TwitterApi api();
 } public final class Dagger_ApiComponent

    implements ApiComponent {
 private Provider<OkHttpClient> provideOkHttpClientProvider;
 private Provider<TwitterApi> provideTwitterApiProvider;
 
 private Dagger_ApiComponent(Builder builder) {
 NetworkModule networkModule = builder.networkModule;
 provideOkHttpClientProvider = ScopedProvider.create( new NetworkModule_ProvideOkHttpClientFactory(networkModule));
 provideTwitterApiProvider = ScopedProvider.create( new NetworkModule_ProvideTwitterApiFactory(networkModule, provideOkHttpClientProvider));
 }
 
 @Override
 public TwitterApi api() {
 return provideTwitterApiProvider.get();
 }
  240. interface ApiComponent {
 TwitterApi api();
 } public final class Dagger_ApiComponent

    implements ApiComponent {
 private Provider<OkHttpClient> provideOkHttpClientProvider;
 private Provider<TwitterApi> provideTwitterApiProvider;
 
 private Dagger_ApiComponent(Builder builder) {
 NetworkModule networkModule = builder.networkModule;
 provideOkHttpClientProvider = ScopedProvider.create( new NetworkModule_ProvideOkHttpClientFactory(networkModule));
 provideTwitterApiProvider = ScopedProvider.create( new NetworkModule_ProvideTwitterApiFactory(networkModule, provideOkHttpClientProvider));
 }
 
 @Override
 public TwitterApi api() {
 return provideTwitterApiProvider.get();
 }
  241. interface ApiComponent {
 TwitterApi api();
 } public final class Dagger_ApiComponent

    implements ApiComponent {
 private Provider<OkHttpClient> provideOkHttpClientProvider;
 private Provider<TwitterApi> provideTwitterApiProvider;
 
 private Dagger_ApiComponent(Builder builder) {
 NetworkModule networkModule = builder.networkModule;
 provideOkHttpClientProvider = ScopedProvider.create( new NetworkModule_ProvideOkHttpClientFactory(networkModule));
 provideTwitterApiProvider = ScopedProvider.create( new NetworkModule_ProvideTwitterApiFactory(networkModule, provideOkHttpClientProvider));
 }
 
 @Override
 public TwitterApi api() {
 return provideTwitterApiProvider.get();
 }
  242. interface ApiComponent {
 TwitterApi api();
 } public final class Dagger_ApiComponent

    implements ApiComponent {
 private Provider<OkHttpClient> provideOkHttpClientProvider;
 private Provider<TwitterApi> provideTwitterApiProvider;
 
 private Dagger_ApiComponent(Builder builder) {
 NetworkModule networkModule = builder.networkModule;
 provideOkHttpClientProvider = ScopedProvider.create( new NetworkModule_ProvideOkHttpClientFactory(networkModule));
 provideTwitterApiProvider = ScopedProvider.create( new NetworkModule_ProvideTwitterApiFactory(networkModule, provideOkHttpClientProvider));
 }
 
 @Override
 public TwitterApi api() {
 return provideTwitterApiProvider.get();
 }
  243. @Module
 public class TwitterModule {
 private final String user;
 


    public TwitterModule(String user) {
 this.user = user;
 }
 
 @Provides
 Tweeter provideTweeter(TwitterApi api) {
 return new Tweeter(api, user);
 }
 
 @Provides
 Timeline provideTimeline(TwitterApi api) {
 return new Timeline(api, user);
 }
 } @Component(
 dependencies = ApiComponent.class,
 modules = TwitterModule.class
 )
 interface TwitterComponent {
 TwitterApplication app();
 }
  244. public final class TwitterModule_ProvideTweeterFactory implements Factory<Tweeter> { 
 private final

    TwitterModule module;
 private final Provider<TwitterApi> apiProvider;
 
 public TwitterModule_ProvideTweeterFactory( TwitterModule module, Provider<TwitterApi> apiProvider) {
 this.module = module;
 this.apiProvider = apiProvider;
 }
 
 @Override
 public Tweeter get() {
 return module.provideTweeter(apiProvider.get());
 }
 }
  245. public final class TwitterModule_ProvideTimelineFactory implements Factory<Timeline> { 
 private final

    TwitterModule module;
 private final Provider<TwitterApi> apiProvider;
 
 public TwitterModule_ProvideTimelineFactory( TwitterModule module, Provider<TwitterApi> apiProvider) {
 this.module = module;
 this.apiProvider = apiProvider;
 }
 
 @Override
 public Timeline get() {
 return module.provideTimeline(apiProvider.get());
 }
 }
  246. public final class TwitterApplication_Factory implements Factory<TwitterApplication> { 
 private final

    Provider<Tweeter> tweeterProvider;
 private final Provider<Timeline> timelineProvider;
 
 public TwitterApplication_Factory( Provider<Tweeter> tweeterProvider, Provider<Timeline> timelineProvider) {
 this.tweeterProvider = tweeterProvider;
 this.timelineProvider = timelineProvider;
 }
 
 @Override
 public TwitterApplication get() {
 return new TwitterApplication(tweeterProvider.get(), timelineProvider.get());
 }
 }
  247. public static final class Builder {
 private TwitterModule twitterModule;
 private

    ApiComponent apiComponent;
 
 public TwitterComponent build() {
 if (twitterModule == null) throw new IllegalStateException("...");
 if (apiComponent == null) throw new IllegalStateException("...");
 return new Dagger_TwitterComponent(this);
 }
 
 public Builder twitterModule(TwitterModule twitterModule) {
 if (twitterModule == null) throw new NullPointerException("twitterModule");
 this.twitterModule = twitterModule;
 return this;
 }
 
 public Builder apiComponent(ApiComponent apiComponent) {
 if (apiComponent == null) throw new NullPointerException("apiComponent");
 this.apiComponent = apiComponent;
 return this;
 }
 }
  248. public static final class Builder {
 private TwitterModule twitterModule;
 private

    ApiComponent apiComponent;
 
 public TwitterComponent build() {
 if (twitterModule == null) throw new IllegalStateException("...");
 if (apiComponent == null) throw new IllegalStateException("...");
 return new Dagger_TwitterComponent(this);
 }
 
 public Builder twitterModule(TwitterModule twitterModule) {
 if (twitterModule == null) throw new NullPointerException("twitterModule");
 this.twitterModule = twitterModule;
 return this;
 }
 
 public Builder apiComponent(ApiComponent apiComponent) {
 if (apiComponent == null) throw new NullPointerException("apiComponent");
 this.apiComponent = apiComponent;
 return this;
 }
 }
  249. public static final class Builder {
 private TwitterModule twitterModule;
 private

    ApiComponent apiComponent;
 
 public TwitterComponent build() {
 if (twitterModule == null) throw new IllegalStateException("...");
 if (apiComponent == null) throw new IllegalStateException("...");
 return new Dagger_TwitterComponent(this);
 }
 
 public Builder twitterModule(TwitterModule twitterModule) {
 if (twitterModule == null) throw new NullPointerException("twitterModule");
 this.twitterModule = twitterModule;
 return this;
 }
 
 public Builder apiComponent(ApiComponent apiComponent) {
 if (apiComponent == null) throw new NullPointerException("apiComponent");
 this.apiComponent = apiComponent;
 return this;
 }
 }
  250. public final class Dagger_TwitterComponent implements TwitterComponent {
 // ...
 


    private Dagger_TwitterComponent(Builder builder) {
 twitterModule = builder.twitterModule;
 apiComponent = builder.apiComponent;
 
 apiProvider = new Factory<TwitterApi>() {
 @Override public TwitterApi get() {
 return apiComponent.api();
 }
 };
 
 provideTweeterProvider = new TwitterModule_ProvideTweeterFactory(twitterModule, apiProvider);
 provideTimelineProvider = new TwitterModule_ProvideTimelineFactory(twitterModule, apiProvider);
 twitterApplicationProvider = new TwitterApplication_Factory( provideTweeterProvider, provideTimelineProvider);
 }
  251. public final class Dagger_TwitterComponent implements TwitterComponent {
 // ...
 


    private Dagger_TwitterComponent(Builder builder) {
 twitterModule = builder.twitterModule;
 apiComponent = builder.apiComponent;
 
 apiProvider = new Factory<TwitterApi>() {
 @Override public TwitterApi get() {
 return apiComponent.api();
 }
 };
 
 provideTweeterProvider = new TwitterModule_ProvideTweeterFactory(twitterModule, apiProvider);
 provideTimelineProvider = new TwitterModule_ProvideTimelineFactory(twitterModule, apiProvider);
 twitterApplicationProvider = new TwitterApplication_Factory( provideTweeterProvider, provideTimelineProvider);
 }
  252. Dagger_ApiComponent.create()

  253. Dagger_ApiComponent.create() new NetworkModule

  254. Dagger_ApiComponent.create() new NetworkModule new NetworkModule_ProvideOkHttpClientFactory new NetworkModule_ProvideTwitterApiFactory

  255. Dagger_ApiComponent.create() new NetworkModule new NetworkModule_ProvideOkHttpClientFactory new NetworkModule_ProvideTwitterApiFactory new TwitterModule("Jake Wharton")

  256. Dagger_ApiComponent.create() new NetworkModule new NetworkModule_ProvideOkHttpClientFactory new NetworkModule_ProvideTwitterApiFactory new TwitterModule("Jake Wharton")

    Dagger_TwitterComponent.builder()...build()
  257. Dagger_ApiComponent.create() new NetworkModule new NetworkModule_ProvideOkHttpClientFactory new NetworkModule_ProvideTwitterApiFactory new TwitterModule("Jake Wharton")

    Dagger_TwitterComponent.builder()...build() new Factory<TwitterApi>
  258. Dagger_ApiComponent.create() new NetworkModule new NetworkModule_ProvideOkHttpClientFactory new NetworkModule_ProvideTwitterApiFactory new TwitterModule("Jake Wharton")

    Dagger_TwitterComponent.builder()...build() new TwitterModule_ProvideTweeterFactory new TwitterModule_ProvideTimelineFactory new TwitterApplication_Factory new Factory<TwitterApi>
  259. twitterComponent.app()

  260. twitterComponent.app() twitterApplicationProvider.get()

  261. twitterComponent.app() twitterApplicationProvider.get() tweeterProvider.get() apiProvider.get() apiComponent.api()

  262. twitterComponent.app() twitterApplicationProvider.get() tweeterProvider.get() apiProvider.get() provideTwitterApiProvider.get() networkModule.provideOkHttpClient() apiComponent.api() clientProvider.get()

  263. twitterComponent.app() twitterApplicationProvider.get() tweeterProvider.get() apiProvider.get() provideTwitterApiProvider.get() networkModule.provideOkHttpClient() apiComponent.api() clientProvider.get() new OkHttpClient()

  264. twitterComponent.app() twitterApplicationProvider.get() tweeterProvider.get() apiProvider.get() provideTwitterApiProvider.get() networkModule.provideOkHttpClient() networkModule.provideTwitterApi(..) apiComponent.api() clientProvider.get() new

    OkHttpClient()
  265. twitterComponent.app() twitterApplicationProvider.get() tweeterProvider.get() apiProvider.get() provideTwitterApiProvider.get() networkModule.provideOkHttpClient() networkModule.provideTwitterApi(..) apiComponent.api() clientProvider.get() new

    OkHttpClient() new TwitterApi(..)
  266. twitterComponent.app() twitterApplicationProvider.get() tweeterProvider.get() apiProvider.get() provideTwitterApiProvider.get() networkModule.provideOkHttpClient() twitterModule.provideTweeter(..) networkModule.provideTwitterApi(..) apiComponent.api() clientProvider.get()

    new OkHttpClient() new TwitterApi(..)
  267. twitterComponent.app() twitterApplicationProvider.get() tweeterProvider.get() apiProvider.get() provideTwitterApiProvider.get() networkModule.provideOkHttpClient() twitterModule.provideTweeter(..) networkModule.provideTwitterApi(..) apiComponent.api() clientProvider.get()

    new OkHttpClient() new TwitterApi(..) new Tweeter(..)
  268. twitterComponent.app() twitterApplicationProvider.get() tweeterProvider.get() apiProvider.get() provideTwitterApiProvider.get() networkModule.provideOkHttpClient() twitterModule.provideTweeter(..) timelineProvider.get() apiProvider.get() networkModule.provideTwitterApi(..)

    apiComponent.api() clientProvider.get() apiComponent.api() new OkHttpClient() new TwitterApi(..) new Tweeter(..)
  269. twitterComponent.app() twitterApplicationProvider.get() tweeterProvider.get() apiProvider.get() provideTwitterApiProvider.get() networkModule.provideOkHttpClient() twitterModule.provideTweeter(..) timelineProvider.get() apiProvider.get() networkModule.provideTwitterApi(..)

    apiComponent.api() clientProvider.get() apiComponent.api() provideTwitterApiProvider.get() new OkHttpClient() new TwitterApi(..) new Tweeter(..)
  270. twitterComponent.app() twitterApplicationProvider.get() tweeterProvider.get() apiProvider.get() provideTwitterApiProvider.get() networkModule.provideOkHttpClient() twitterModule.provideTweeter(..) timelineProvider.get() apiProvider.get() networkModule.provideTwitterApi(..)

    apiComponent.api() clientProvider.get() apiComponent.api() provideTwitterApiProvider.get() twitterModule.provideTimeline(..) new OkHttpClient() new TwitterApi(..) new Tweeter(..)
  271. twitterComponent.app() twitterApplicationProvider.get() tweeterProvider.get() apiProvider.get() provideTwitterApiProvider.get() networkModule.provideOkHttpClient() twitterModule.provideTweeter(..) timelineProvider.get() apiProvider.get() networkModule.provideTwitterApi(..)

    apiComponent.api() clientProvider.get() apiComponent.api() provideTwitterApiProvider.get() twitterModule.provideTimeline(..) new OkHttpClient() new TwitterApi(..) new Tweeter(..) new Timeline(..)
  272. twitterComponent.app() twitterApplicationProvider.get() tweeterProvider.get() apiProvider.get() provideTwitterApiProvider.get() networkModule.provideOkHttpClient() twitterModule.provideTweeter(..) timelineProvider.get() apiProvider.get() networkModule.provideTwitterApi(..)

    apiComponent.api() clientProvider.get() apiComponent.api() provideTwitterApiProvider.get() twitterModule.provideTimeline(..) new TwitterApplication(..) new OkHttpClient() new TwitterApi(..) new Tweeter(..) new Timeline(..)
  273. Annotation Processing

  274. Annotation Processing bit.ly/apt-bd

  275. JSR 330

  276. public @interface Inject {} public @interface Qualifier {} public @interface

    Named {
 String value();
 } public interface Provider<T> {
 T get();
 } public @interface Scope {} JSR 330 public @interface Singleton {}
  277. Dagger 1

  278. public abstract class ObjectGraph {
 public static ObjectGraph create(Object... modules)

    {}
 public abstract ObjectGraph plus(Object... modules);
 public abstract void validate();
 public abstract void injectStatics();
 public abstract <T> T get(Class<T> type);
 public abstract <T> T inject(T instance);
 } public interface Lazy<T> {
 T get();
 } public @interface Module {
 Class<?>[] injects() default { };
 Class<?>[] staticInjections() default { };
 Class<?>[] includes() default { };
 Class<?> addsTo() default Void.class;
 boolean overrides() default false;
 boolean complete() default true;
 boolean library() default true;
 } public @interface Provides {
 enum Type { UNIQUE, SET }
 Type type() default Type.UNIQUE;
 } public interface MembersInjector<T> {
 void injectMembers(T instance);
 } Dagger 1
  279. public abstract class ObjectGraph {
 public static ObjectGraph create(Object... modules)

    {}
 public abstract ObjectGraph plus(Object... modules);
 public abstract void validate();
 public abstract void injectStatics();
 public abstract <T> T get(Class<T> type);
 public abstract <T> T inject(T instance);
 } public interface Lazy<T> {
 T get();
 } public @interface Module {
 Class<?>[] injects() default { };
 Class<?>[] staticInjections() default { };
 Class<?>[] includes() default { };
 Class<?> addsTo() default Void.class;
 boolean overrides() default false;
 boolean complete() default true;
 boolean library() default true;
 } public @interface Provides {
 enum Type { UNIQUE, SET }
 Type type() default Type.UNIQUE;
 } public interface MembersInjector<T> {
 void injectMembers(T instance);
 } Dagger 1 public interface Lazy<T> {
 T get();
 } public interface MembersInjector<T> {
 void injectMembers(T instance);
 } public @interface Module {
 Class<?>[] injects() default { };
 Class<?>[] staticInjections() default { };
 Class<?>[] includes() default { };
 Class<?> addsTo() default Void.class;
 boolean overrides() default false;
 boolean complete() default true;
 boolean library() default true;
 } public abstract class ObjectGraph {
 public static ObjectGraph create(Object... modules) {}
 public abstract ObjectGraph plus(Object... modules);
 public abstract void validate();
 public abstract void injectStatics();
 public abstract <T> T get(Class<T> type);
 public abstract <T> T inject(T instance);
 }
  280. Dagger 2

  281. public @interface Component {
 Class<?>[] modules() default {};
 Class<?>[] dependencies()

    default {};
 } public interface Lazy<T> {
 T get();
 } public @interface Module {
 Class<?>[] includes() default { };
 } public @interface Provides {
 } public @interface MapKey {
 boolean unwrapValue();
 } Dagger 2
  282. public @interface Component {
 Class<?>[] modules() default {};
 Class<?>[] dependencies()

    default {};
 } public interface Lazy<T> {
 T get();
 } public @interface Module {
 Class<?>[] includes() default { };
 } public @interface Provides {
 } public @interface MapKey {
 boolean unwrapValue();
 } Dagger 2 public interface Lazy<T> {
 T get();
 } public @interface MapKey {
 boolean unwrapValue();
 }
  283. More Concepts

  284. More Concepts • Set and map bindings.

  285. More Concepts • Set and map bindings. • Asynchronous producers.

  286. More Concepts • Set and map bindings. • Asynchronous producers.

    • Testing and module overrides.
  287. More Concepts • Set and map bindings. • Asynchronous producers.

    • Testing and module overrides. • AutoFactory for assisted injection.
  288. github.com/google/dagger

  289. Questions?

  290. Questions? jakewharton jakewharton jakewharton twitter.com/ google.com/+ .com

  291. None