google / dagger

A fast dependency injector for Android and Java.
https://dagger.dev
Apache License 2.0
17.42k stars 2.01k forks source link

Two subcomponents with the same name, in the different packages/classes, connected to the same parent #261

Closed henieek closed 8 years ago

henieek commented 8 years ago

Hey there,

I tried to find some existing reports regarding this issue but I couldn't find anything related.

My usecase: I use Dagger2 in my Android app and I have one, big ApplicationComponent that keeps all the application-wide dependencies. Then I have bunch of subcomponents, that are connecting to the ApplicationComponent extending it by some additional dependencies. These subcomponents (and their modules) are inner interfaces and inner classes residing within injectee-classes scopes. E.g.:

public class MyCoolAndroidService extends Service {
 // stuff

 @Subcomponent(modules = DaggerModule.class)
 public interface DaggerComponent {
   // stuff
 }

@Module
 public static class DaggerModule {
   // stuff
 }

And then within the ApplicationComponent:

@Component(modules = ApplicationModule.class)
@ApplicationScope
public interface ApplicationComponent {

  MyCoolAndroidService.DaggerComponent plus(MyCoolAndroidService.DaggerModule module);
  // about 20 plus methods more here
}

I wanted to avoid creating monster-looking names like MyCoolAndroidServiceComponent and MyCoolAndroidServiceModule thus I planned to keep all these names as above. Unfortunately - it seems to be impossible task with Dagger2 due to its way of generating code. The outcome for me is:

  1. DaggerApplicationComponent class is generated
  2. Two inner classes, both with name "DaggerComponentImpl" are generated, thus it results in classname duplication error in the compile time.

(Note: the same thing happens if your same-named subcomponents are top-level classes, but reside in two different packages).

Is it something you know about already? I may come up with some pull-request fixing that issue if you think it would be helpful.

ronshapiro commented 8 years ago

Looks like this is a partial duplicate of #236, with the addition that same Subcomponents in different packages with the same name must be deduped as well.

henieek commented 8 years ago

@ronshapiro I prepared a fix for this, seems like it works well for my app. Tests are passing, not sure if it doesn't break anything though. Check it out: https://github.com/partition/dagger/commit/66f5bcf38223257db03a8aa53a4ad7f75618eade

ronshapiro commented 8 years ago

A fix for this was submitted internally (and will be linked to this issue when synced with Github). When conflicting simple names are encountered, we're going to continue prepending parts of the FQCN to the Subcomponent impl name until we get unique names. So in the case of com.example.Bar.Foo and com.example.baz.Foo you'd get Bar_FooImpland baz_FooImpl.