1 /*
2  * Copyright (C) 2017 The Android Open Source Project
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 @file:Suppress("AddVarianceModifier")
18 
19 package androidx.room.processor.cache
20 
21 import androidx.room.processor.FieldProcessor
22 import androidx.room.vo.EmbeddedField
23 import androidx.room.vo.Entity
24 import androidx.room.vo.Pojo
25 import androidx.room.vo.Warning
26 import java.util.LinkedHashSet
27 import javax.lang.model.element.Element
28 import javax.lang.model.type.TypeMirror
29 
30 /**
31  * A cache key can be used to avoid re-processing elements.
32  * <p>
33  * Each context has a cache variable that uses the same backing storage as the Root Context but
34  * adds current adapters and warning suppression list to the key.
35  */
36 class Cache(val parent: Cache?, val converters: LinkedHashSet<TypeMirror>,
37             val suppressedWarnings: Set<Warning>) {
38     val entities: Bucket<EntityKey, Entity> = Bucket(parent?.entities)
39     val pojos: Bucket<PojoKey, Pojo> = Bucket(parent?.pojos)
40 
41     inner class Bucket<K, T>(source: Bucket<K, T>?) {
42         private val entries: MutableMap<FullKey<K>, T> = source?.entries ?: mutableMapOf()
getnull43         fun get(key: K, calculate: () -> T): T {
44             val fullKey = FullKey(converters, suppressedWarnings, key)
45             return entries.getOrPut(fullKey, {
46                 calculate()
47             })
48         }
49     }
50 
51     /**
52      * Key for Entity cache
53      */
54     data class EntityKey(val element: Element)
55 
56     /**
57      * Key for Pojo cache
58      */
59     data class PojoKey(
60             val element: Element,
61             val scope: FieldProcessor.BindingScope,
62             val parent: EmbeddedField?)
63 
64     /**
65      * Internal key representation with adapters & warnings included.
66      * <p>
67      * Converters are kept in a linked set since the order is important for the TypeAdapterStore.
68      */
69     private data class FullKey<T>(
70             val converters: LinkedHashSet<TypeMirror>,
71             val suppressedWarnings: Set<Warning>,
72             val key: T)
73 }
74