xref: /aosp_15_r20/external/dagger2/javatests/dagger/functional/kotlinsrc/cycle/Cycles.kt (revision f585d8a307d0621d6060bd7e80091fdcbf94fe27)
1 /*
2  * Copyright (C) 2022 The Dagger Authors.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package dagger.functional.kotlinsrc.cycle
18 
19 import dagger.Binds
20 import dagger.Component
21 import dagger.Lazy
22 import dagger.Module
23 import dagger.Provides
24 import dagger.Subcomponent
25 import dagger.multibindings.IntoMap
26 import dagger.multibindings.StringKey
27 import javax.inject.Inject
28 import javax.inject.Provider
29 import kotlin.jvm.JvmSuppressWildcards
30 
31 /**
32  * Cycle classes used for testing cyclic dependencies.
33  *
34  * `A <= (E <= D <= B <= C <= Provider<A>, Lazy<A>), (B <= C <= Provider<A>, Lazy<A>)`
35  * `S <= Provider<S>, Lazy<S>`
36  */
37 @Suppress("BadInject")
38 class Cycles private constructor() {
39   class A @Inject constructor(val e: E, val b: B)
40   class B @Inject constructor(val c: C)
41   class C @Inject constructor(val aProvider: Provider<A>) {
42     @Inject lateinit var aLazy: Lazy<A>
43     @Inject lateinit var aLazyProvider: Provider<Lazy<A>>
44   }
45   class D @Inject constructor(val b: B)
46   class E @Inject constructor(val d: D)
47   class S @Inject constructor(val sProvider: Provider<S>) {
48     @Inject lateinit var sLazy: Lazy<S>
49   }
50   class X @Inject constructor(val y: Y)
51   class Y @Inject constructor(
52     val mapOfProvidersOfX: Map<String, @JvmSuppressWildcards Provider<X>>,
53     val mapOfProvidersOfY: Map<String, @JvmSuppressWildcards Provider<Y>>
54   )
55 
56   @Module
57   internal abstract class CycleMapModule {
58     @Binds
59     @IntoMap
60     @StringKey("X")
xnull61     abstract fun x(x: X): X
62 
63     @Binds
64     @IntoMap
65     @StringKey("Y")
66     abstract fun y(y: Y): Y
67   }
68 
69   @Component(modules = [CycleMapModule::class])
70   interface CycleMapComponent {
71     fun y(): Y
72   }
73 
74   @Component(modules = [CycleModule::class])
75   interface CycleComponent {
anull76     fun a(): A
77     fun c(): C
78     fun child(): ChildCycleComponent
79   }
80 
81   @Module
82   internal object CycleModule {
83     @Provides
84     fun provideObjectWithCycle(
85       @Suppress("UNUSED_PARAMETER") someObject: Provider<Any>
86     ): Any = "object"
87   }
88 
89   @Component
90   interface SelfCycleComponent {
snull91     fun s(): S
92   }
93 
94   @Subcomponent
95   interface ChildCycleComponent {
96     fun a(): A
97     fun someObject(): Any
98   }
99 
100   interface Foo
101   class Bar @Inject constructor(
102     @Suppress("UNUSED_PARAMETER") fooProvider: Provider<Foo>
103   ) : Foo
104 
105   /**
106    * A component with a cycle in which a `@Binds` binding depends on the binding that has to be
107    * deferred.
108    */
109   @Component(modules = [BindsCycleModule::class])
110   interface BindsCycleComponent {
barnull111     fun bar(): Bar
112   }
113 
114   @Module
115   internal abstract class BindsCycleModule {
116     @Binds abstract fun foo(bar: Bar): Foo
117   }
118 }
119