/*
 * Copyright (C) 2016 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package androidx.room.solver

import androidx.annotation.VisibleForTesting
import androidx.room.compiler.codegen.CodeLanguage
import androidx.room.compiler.codegen.XTypeName
import androidx.room.compiler.processing.XNullability
import androidx.room.compiler.processing.XType
import androidx.room.compiler.processing.isArray
import androidx.room.compiler.processing.isEnum
import androidx.room.ext.CollectionTypeNames.ARRAY_MAP
import androidx.room.ext.CollectionTypeNames.INT_SPARSE_ARRAY
import androidx.room.ext.CollectionTypeNames.LONG_SPARSE_ARRAY
import androidx.room.ext.CommonTypeNames
import androidx.room.ext.GuavaTypeNames
import androidx.room.ext.getValueClassUnderlyingProperty
import androidx.room.ext.isByteBuffer
import androidx.room.ext.isEntityElement
import androidx.room.ext.isNotByte
import androidx.room.ext.isNotKotlinUnit
import androidx.room.ext.isNotVoid
import androidx.room.ext.isNotVoidObject
import androidx.room.ext.isUUID
import androidx.room.parser.ParsedQuery
import androidx.room.parser.SQLTypeAffinity
import androidx.room.preconditions.checkTypeOrNull
import androidx.room.processor.Context
import androidx.room.processor.EntityProcessor
import androidx.room.processor.FieldProcessor
import androidx.room.processor.PojoProcessor
import androidx.room.processor.ProcessorErrors
import androidx.room.processor.ProcessorErrors.DO_NOT_USE_GENERIC_IMMUTABLE_MULTIMAP
import androidx.room.solver.binderprovider.CoroutineFlowResultBinderProvider
import androidx.room.solver.binderprovider.CursorQueryResultBinderProvider
import androidx.room.solver.binderprovider.DataSourceFactoryQueryResultBinderProvider
import androidx.room.solver.binderprovider.DataSourceQueryResultBinderProvider
import androidx.room.solver.binderprovider.GuavaListenableFutureQueryResultBinderProvider
import androidx.room.solver.binderprovider.InstantQueryResultBinderProvider
import androidx.room.solver.binderprovider.ListenableFuturePagingSourceQueryResultBinderProvider
import androidx.room.solver.binderprovider.LiveDataQueryResultBinderProvider
import androidx.room.solver.binderprovider.PagingSourceQueryResultBinderProvider
import androidx.room.solver.binderprovider.RxCallableQueryResultBinderProvider
import androidx.room.solver.binderprovider.RxJava2PagingSourceQueryResultBinderProvider
import androidx.room.solver.binderprovider.RxJava3PagingSourceQueryResultBinderProvider
import androidx.room.solver.binderprovider.RxQueryResultBinderProvider
import androidx.room.solver.prepared.binder.PreparedQueryResultBinder
import androidx.room.solver.prepared.binderprovider.GuavaListenableFuturePreparedQueryResultBinderProvider
import androidx.room.solver.prepared.binderprovider.InstantPreparedQueryResultBinderProvider
import androidx.room.solver.prepared.binderprovider.PreparedQueryResultBinderProvider
import androidx.room.solver.prepared.binderprovider.RxPreparedQueryResultBinderProvider
import androidx.room.solver.prepared.result.PreparedQueryResultAdapter
import androidx.room.solver.query.parameter.ArrayQueryParameterAdapter
import androidx.room.solver.query.parameter.BasicQueryParameterAdapter
import androidx.room.solver.query.parameter.CollectionQueryParameterAdapter
import androidx.room.solver.query.parameter.QueryParameterAdapter
import androidx.room.solver.query.result.ArrayQueryResultAdapter
import androidx.room.solver.query.result.EntityRowAdapter
import androidx.room.solver.query.result.GuavaImmutableMultimapQueryResultAdapter
import androidx.room.solver.query.result.GuavaOptionalQueryResultAdapter
import androidx.room.solver.query.result.ImmutableListQueryResultAdapter
import androidx.room.solver.query.result.ImmutableMapQueryResultAdapter
import androidx.room.solver.query.result.ListQueryResultAdapter
import androidx.room.solver.query.result.MapQueryResultAdapter
import androidx.room.solver.query.result.MultimapQueryResultAdapter
import androidx.room.solver.query.result.MultimapQueryResultAdapter.Companion.validateMapTypeArgs
import androidx.room.solver.query.result.MultimapQueryResultAdapter.MapType.Companion.isSparseArray
import androidx.room.solver.query.result.OptionalQueryResultAdapter
import androidx.room.solver.query.result.PojoRowAdapter
import androidx.room.solver.query.result.QueryResultAdapter
import androidx.room.solver.query.result.QueryResultBinder
import androidx.room.solver.query.result.RowAdapter
import androidx.room.solver.query.result.SingleColumnRowAdapter
import androidx.room.solver.query.result.SingleItemQueryResultAdapter
import androidx.room.solver.query.result.SingleNamedColumnRowAdapter
import androidx.room.solver.shortcut.binder.DeleteOrUpdateMethodBinder
import androidx.room.solver.shortcut.binder.InsertOrUpsertMethodBinder
import androidx.room.solver.shortcut.binderprovider.DeleteOrUpdateMethodBinderProvider
import androidx.room.solver.shortcut.binderprovider.GuavaListenableFutureDeleteOrUpdateMethodBinderProvider
import androidx.room.solver.shortcut.binderprovider.GuavaListenableFutureInsertMethodBinderProvider
import androidx.room.solver.shortcut.binderprovider.GuavaListenableFutureUpsertMethodBinderProvider
import androidx.room.solver.shortcut.binderprovider.InsertOrUpsertMethodBinderProvider
import androidx.room.solver.shortcut.binderprovider.InstantDeleteOrUpdateMethodBinderProvider
import androidx.room.solver.shortcut.binderprovider.InstantInsertMethodBinderProvider
import androidx.room.solver.shortcut.binderprovider.InstantUpsertMethodBinderProvider
import androidx.room.solver.shortcut.binderprovider.RxCallableDeleteOrUpdateMethodBinderProvider
import androidx.room.solver.shortcut.binderprovider.RxCallableInsertMethodBinderProvider
import androidx.room.solver.shortcut.binderprovider.RxCallableUpsertMethodBinderProvider
import androidx.room.solver.shortcut.result.DeleteOrUpdateMethodAdapter
import androidx.room.solver.shortcut.result.InsertOrUpsertMethodAdapter
import androidx.room.solver.types.BoxedBooleanToBoxedIntConverter
import androidx.room.solver.types.BoxedPrimitiveColumnTypeAdapter
import androidx.room.solver.types.ByteArrayColumnTypeAdapter
import androidx.room.solver.types.ByteBufferColumnTypeAdapter
import androidx.room.solver.types.ColumnTypeAdapter
import androidx.room.solver.types.CompositeAdapter
import androidx.room.solver.types.CursorValueReader
import androidx.room.solver.types.EnumColumnTypeAdapter
import androidx.room.solver.types.PrimitiveBooleanToIntConverter
import androidx.room.solver.types.PrimitiveColumnTypeAdapter
import androidx.room.solver.types.StatementValueBinder
import androidx.room.solver.types.StringColumnTypeAdapter
import androidx.room.solver.types.TypeConverter
import androidx.room.solver.types.UuidColumnTypeAdapter
import androidx.room.solver.types.ValueClassConverterWrapper
import androidx.room.vo.BuiltInConverterFlags
import androidx.room.vo.MapInfo
import androidx.room.vo.ShortcutQueryParameter
import androidx.room.vo.Warning
import androidx.room.vo.isEnabled
import com.google.common.collect.ImmutableList
import com.google.common.collect.ImmutableListMultimap
import com.google.common.collect.ImmutableMap
import com.google.common.collect.ImmutableMultimap
import com.google.common.collect.ImmutableSetMultimap

/**
 * Holds all type adapters and can create on demand composite type adapters to convert a type into a
 * database column.
 */
class TypeAdapterStore private constructor(
    val context: Context,
    /**
     * first type adapter has the highest priority
     */
    private val columnTypeAdapters: List<ColumnTypeAdapter>,
    @get:VisibleForTesting
    internal val typeConverterStore: TypeConverterStore,
    private val builtInConverterFlags: BuiltInConverterFlags
) {

    companion object {
        fun copy(context: Context, store: TypeAdapterStore): TypeAdapterStore {
            return TypeAdapterStore(
                context = context,
                columnTypeAdapters = store.columnTypeAdapters,
                typeConverterStore = store.typeConverterStore,
                builtInConverterFlags = store.builtInConverterFlags
            )
        }

        fun create(
            context: Context,
            builtInConverterFlags: BuiltInConverterFlags,
            vararg extras: Any
        ): TypeAdapterStore {
            val adapters = arrayListOf<ColumnTypeAdapter>()
            val converters = arrayListOf<TypeConverter>()
            fun addAny(extra: Any?) {
                when (extra) {
                    is TypeConverter -> converters.add(extra)
                    is ColumnTypeAdapter -> adapters.add(extra)
                    is List<*> -> extra.forEach(::addAny)
                    else -> throw IllegalArgumentException("unknown extra $extra")
                }
            }

            extras.forEach(::addAny)
            fun addTypeConverter(converter: TypeConverter) {
                converters.add(converter)
            }

            fun addColumnAdapter(adapter: ColumnTypeAdapter) {
                adapters.add(adapter)
            }

            val primitives = PrimitiveColumnTypeAdapter
                .createPrimitiveAdapters(context.processingEnv)
            primitives.forEach(::addColumnAdapter)
            BoxedPrimitiveColumnTypeAdapter
                .createBoxedPrimitiveAdapters(primitives)
                .forEach(::addColumnAdapter)
            StringColumnTypeAdapter.create(context.processingEnv).forEach(::addColumnAdapter)
            ByteArrayColumnTypeAdapter.create(context.processingEnv).forEach(::addColumnAdapter)
            PrimitiveBooleanToIntConverter.create(context.processingEnv).forEach(::addTypeConverter)
            // null aware converter is able to automatically null wrap converters so we don't
            // need this as long as we are running in KSP
            BoxedBooleanToBoxedIntConverter.create(context.processingEnv)
                .forEach(::addTypeConverter)
            return TypeAdapterStore(
                context = context, columnTypeAdapters = adapters,
                typeConverterStore = TypeConverterStore.create(
                    context = context,
                    typeConverters = converters,
                    knownColumnTypes = adapters.map { it.out }
                ),
                builtInConverterFlags = builtInConverterFlags
            )
        }
    }

    private val queryResultBinderProviders: List<QueryResultBinderProvider> =
        mutableListOf<QueryResultBinderProvider>().apply {
            add(CursorQueryResultBinderProvider(context))
            add(LiveDataQueryResultBinderProvider(context))
            add(GuavaListenableFutureQueryResultBinderProvider(context))
            addAll(RxQueryResultBinderProvider.getAll(context))
            addAll(RxCallableQueryResultBinderProvider.getAll(context))
            add(DataSourceQueryResultBinderProvider(context))
            add(DataSourceFactoryQueryResultBinderProvider(context))
            add(RxJava2PagingSourceQueryResultBinderProvider(context))
            add(RxJava3PagingSourceQueryResultBinderProvider(context))
            add(ListenableFuturePagingSourceQueryResultBinderProvider(context))
            add(PagingSourceQueryResultBinderProvider(context))
            add(CoroutineFlowResultBinderProvider(context))
            add(InstantQueryResultBinderProvider(context))
        }

    private val preparedQueryResultBinderProviders: List<PreparedQueryResultBinderProvider> =
        mutableListOf<PreparedQueryResultBinderProvider>().apply {
            addAll(RxPreparedQueryResultBinderProvider.getAll(context))
            add(GuavaListenableFuturePreparedQueryResultBinderProvider(context))
            add(InstantPreparedQueryResultBinderProvider(context))
        }

    private val insertBinderProviders: List<InsertOrUpsertMethodBinderProvider> =
        mutableListOf<InsertOrUpsertMethodBinderProvider>().apply {
            addAll(RxCallableInsertMethodBinderProvider.getAll(context))
            add(GuavaListenableFutureInsertMethodBinderProvider(context))
            add(InstantInsertMethodBinderProvider(context))
        }

    private val deleteOrUpdateBinderProvider: List<DeleteOrUpdateMethodBinderProvider> =
        mutableListOf<DeleteOrUpdateMethodBinderProvider>().apply {
            addAll(RxCallableDeleteOrUpdateMethodBinderProvider.getAll(context))
            add(GuavaListenableFutureDeleteOrUpdateMethodBinderProvider(context))
            add(InstantDeleteOrUpdateMethodBinderProvider(context))
        }

    private val upsertBinderProviders: List<InsertOrUpsertMethodBinderProvider> =
        mutableListOf<InsertOrUpsertMethodBinderProvider>().apply {
            addAll(RxCallableUpsertMethodBinderProvider.getAll(context))
            add(GuavaListenableFutureUpsertMethodBinderProvider(context))
            add(InstantUpsertMethodBinderProvider(context))
        }

    /**
     * Searches 1 way to bind a value into a statement.
     */
    fun findStatementValueBinder(
        input: XType,
        affinity: SQLTypeAffinity?
    ): StatementValueBinder? {
        if (input.isError()) {
            return null
        }
        val adapter = findDirectAdapterFor(input, affinity)
        if (adapter != null) {
            return adapter
        }

        fun findTypeConverterAdapter(): ColumnTypeAdapter? {
            val targetTypes = affinity?.getTypeMirrors(context.processingEnv)
            val binder = typeConverterStore.findConverterIntoStatement(
                input = input,
                columnTypes = targetTypes
            ) ?: return null
            // columnAdapter should not be null but we are receiving errors on crash in `first()` so
            // this safeguard allows us to dispatch the real problem to the user (e.g. why we couldn't
            // find the right adapter)
            val columnAdapter = getAllColumnAdapters(binder.to).firstOrNull() ?: return null
            return CompositeAdapter(input, columnAdapter, binder, null)
        }

        val adapterByTypeConverter = findTypeConverterAdapter()
        if (adapterByTypeConverter != null) {
            return adapterByTypeConverter
        }
        val defaultAdapter = createDefaultTypeAdapter(input, affinity)
        if (defaultAdapter != null) {
            return defaultAdapter
        }
        return null
    }

    /**
     * Searches 1 way to read it from cursor
     */
    fun findCursorValueReader(output: XType, affinity: SQLTypeAffinity?): CursorValueReader? {
        if (output.isError()) {
            return null
        }
        val adapter = findColumnTypeAdapter(output, affinity, skipDefaultConverter = true)
        if (adapter != null) {
            // two way is better
            return adapter
        }

        fun findTypeConverterAdapter(): ColumnTypeAdapter? {
            val targetTypes = affinity?.getTypeMirrors(context.processingEnv)
            val converter = typeConverterStore.findConverterFromCursor(
                columnTypes = targetTypes,
                output = output
            ) ?: return null
            return CompositeAdapter(
                output,
                getAllColumnAdapters(converter.from).first(), null, converter
            )
        }

        // we could not find a two way version, search for anything
        val typeConverterAdapter = findTypeConverterAdapter()
        if (typeConverterAdapter != null) {
            return typeConverterAdapter
        }

        val defaultAdapter = createDefaultTypeAdapter(output, affinity)
        if (defaultAdapter != null) {
            return defaultAdapter
        }

        return null
    }

    /**
     * Finds a two way converter, if you need 1 way, use findStatementValueBinder or
     * findCursorValueReader.
     */
    fun findColumnTypeAdapter(
        out: XType,
        affinity: SQLTypeAffinity?,
        skipDefaultConverter: Boolean
    ): ColumnTypeAdapter? {
        if (out.isError()) {
            return null
        }
        val adapter = findDirectAdapterFor(out, affinity)
        if (adapter != null) {
            return adapter
        }

        fun findTypeConverterAdapter(): ColumnTypeAdapter? {
            val targetTypes = affinity?.getTypeMirrors(context.processingEnv)
            val intoStatement = typeConverterStore.findConverterIntoStatement(
                input = out,
                columnTypes = targetTypes
            ) ?: return null
            // ok found a converter, try the reverse now
            val fromCursor = typeConverterStore.reverse(intoStatement)
                ?: typeConverterStore.findTypeConverter(intoStatement.to, out) ?: return null
            return CompositeAdapter(
                out, getAllColumnAdapters(intoStatement.to).first(), intoStatement, fromCursor
            )
        }

        val adapterByTypeConverter = findTypeConverterAdapter()
        if (adapterByTypeConverter != null) {
            return adapterByTypeConverter
        }

        if (!skipDefaultConverter) {
            val defaultAdapter = createDefaultTypeAdapter(out, affinity)
            if (defaultAdapter != null) {
                return defaultAdapter
            }
        }
        return null
    }

    private fun createDefaultTypeAdapter(
        type: XType,
        affinity: SQLTypeAffinity?
    ): ColumnTypeAdapter? {
        val typeElement = type.typeElement
        if (typeElement?.isValueClass() == true) {
            // Extract the type value of the Value class element
            val underlyingProperty = typeElement.getValueClassUnderlyingProperty()
            val underlyingTypeColumnAdapter = findColumnTypeAdapter(
                out = underlyingProperty.asMemberOf(type),
                affinity = affinity,
                skipDefaultConverter = false
            ) ?: return null

            return ValueClassConverterWrapper(
                valueTypeColumnAdapter = underlyingTypeColumnAdapter,
                affinity = underlyingTypeColumnAdapter.typeAffinity,
                out = type,
                valuePropertyName = underlyingProperty.name
            )
        }
        return when {
            builtInConverterFlags.enums.isEnabled() &&
                typeElement?.isEnum() == true -> EnumColumnTypeAdapter(typeElement, type)
            builtInConverterFlags.uuid.isEnabled() &&
                type.isUUID() -> UuidColumnTypeAdapter(type)
            builtInConverterFlags.byteBuffer.isEnabled() &&
                type.isByteBuffer() -> ByteBufferColumnTypeAdapter(type)
            else -> null
        }
    }

    private fun findDirectAdapterFor(
        out: XType,
        affinity: SQLTypeAffinity?
    ): ColumnTypeAdapter? {
        return getAllColumnAdapters(out).firstOrNull {
            affinity == null || it.typeAffinity == affinity
        }
    }

    fun findDeleteOrUpdateMethodBinder(typeMirror: XType): DeleteOrUpdateMethodBinder {
        return deleteOrUpdateBinderProvider.first {
            it.matches(typeMirror)
        }.provide(typeMirror)
    }

    fun findInsertMethodBinder(
        typeMirror: XType,
        params: List<ShortcutQueryParameter>
    ): InsertOrUpsertMethodBinder {
        return insertBinderProviders.first {
            it.matches(typeMirror)
        }.provide(typeMirror, params)
    }

    fun findUpsertMethodBinder(
        typeMirror: XType,
        params: List<ShortcutQueryParameter>
    ): InsertOrUpsertMethodBinder {
        return upsertBinderProviders.first {
            it.matches(typeMirror)
        }.provide(typeMirror, params)
    }

    fun findQueryResultBinder(
        typeMirror: XType,
        query: ParsedQuery,
        extrasCreator: TypeAdapterExtras.() -> Unit = { }
    ): QueryResultBinder {
        return findQueryResultBinder(typeMirror, query, TypeAdapterExtras().apply(extrasCreator))
    }

    fun findQueryResultBinder(
        typeMirror: XType,
        query: ParsedQuery,
        extras: TypeAdapterExtras
    ): QueryResultBinder {
        return queryResultBinderProviders.first {
            it.matches(typeMirror)
        }.provide(typeMirror, query, extras)
    }

    fun findPreparedQueryResultBinder(
        typeMirror: XType,
        query: ParsedQuery
    ): PreparedQueryResultBinder {
        return preparedQueryResultBinderProviders.first {
            it.matches(typeMirror)
        }.provide(typeMirror, query)
    }

    fun findPreparedQueryResultAdapter(typeMirror: XType, query: ParsedQuery) =
        PreparedQueryResultAdapter.create(typeMirror, query.type)

    fun findDeleteOrUpdateAdapter(typeMirror: XType): DeleteOrUpdateMethodAdapter? {
        return DeleteOrUpdateMethodAdapter.create(typeMirror)
    }

    fun findInsertAdapter(
        typeMirror: XType,
        params: List<ShortcutQueryParameter>
    ): InsertOrUpsertMethodAdapter? {
        return InsertOrUpsertMethodAdapter.createInsert(context, typeMirror, params)
    }

    fun findUpsertAdapter(
        typeMirror: XType,
        params: List<ShortcutQueryParameter>
    ): InsertOrUpsertMethodAdapter? {
        return InsertOrUpsertMethodAdapter.createUpsert(context, typeMirror, params)
    }

    fun findQueryResultAdapter(
        typeMirror: XType,
        query: ParsedQuery,
        extrasCreator: TypeAdapterExtras.() -> Unit = { }
    ): QueryResultAdapter? {
        return findQueryResultAdapter(typeMirror, query, TypeAdapterExtras().apply(extrasCreator))
    }

    fun findQueryResultAdapter(
        typeMirror: XType,
        query: ParsedQuery,
        extras: TypeAdapterExtras
    ): QueryResultAdapter? {
        if (typeMirror.isError()) {
            return null
        }

        // TODO: (b/192068912) Refactor the following since this if-else cascade has gotten large
        if (typeMirror.isArray() && typeMirror.componentType.isNotByte()) {
            checkTypeNullability(
                typeMirror,
                extras,
                "Array",
                arrayComponentType = typeMirror.componentType
            )
            val rowAdapter =
                findRowAdapter(typeMirror.componentType, query) ?: return null
            return ArrayQueryResultAdapter(typeMirror, rowAdapter)
        } else if (typeMirror.typeArguments.isEmpty()) {
            val rowAdapter = findRowAdapter(typeMirror, query) ?: return null
            return SingleItemQueryResultAdapter(rowAdapter)
        } else if (typeMirror.rawType.asTypeName() == GuavaTypeNames.OPTIONAL) {
            checkTypeNullability(
                typeMirror,
                extras,
                "Optional"
            )
            // Handle Guava Optional by unpacking its generic type argument and adapting that.
            // The Optional adapter will re-append the Optional type.
            val typeArg = typeMirror.typeArguments.first()
            // use nullable when finding row adapter as non-null adapters might return
            // default values
            val rowAdapter = findRowAdapter(typeArg.makeNullable(), query) ?: return null
            return GuavaOptionalQueryResultAdapter(
                typeArg = typeArg,
                resultAdapter = SingleItemQueryResultAdapter(rowAdapter)
            )
        } else if (typeMirror.rawType.asTypeName() == CommonTypeNames.OPTIONAL) {
            checkTypeNullability(
                typeMirror,
                extras,
                "Optional"
            )

            // Handle java.util.Optional similarly.
            val typeArg = typeMirror.typeArguments.first()
            // use nullable when finding row adapter as non-null adapters might return
            // default values
            val rowAdapter = findRowAdapter(typeArg.makeNullable(), query) ?: return null
            return OptionalQueryResultAdapter(
                typeArg = typeArg,
                resultAdapter = SingleItemQueryResultAdapter(rowAdapter)
            )
        } else if (typeMirror.isTypeOf(ImmutableList::class)) {
            checkTypeNullability(
                typeMirror,
                extras
            )

            val typeArg = typeMirror.typeArguments.first().extendsBoundOrSelf()
            val rowAdapter = findRowAdapter(typeArg, query) ?: return null
            return ImmutableListQueryResultAdapter(
                typeArg = typeArg,
                rowAdapter = rowAdapter
            )
        } else if (typeMirror.isTypeOf(java.util.List::class)) {
            checkTypeNullability(
                typeMirror,
                extras
            )

            val typeArg = typeMirror.typeArguments.first().extendsBoundOrSelf()
            val rowAdapter = findRowAdapter(typeArg, query) ?: return null
            return ListQueryResultAdapter(
                typeArg = typeArg,
                rowAdapter = rowAdapter
            )
        } else if (typeMirror.isTypeOf(ImmutableMap::class)) {
            val keyTypeArg = typeMirror.typeArguments[0].extendsBoundOrSelf()
            val valueTypeArg = typeMirror.typeArguments[1].extendsBoundOrSelf()
            checkTypeNullability(typeMirror, extras)

            // Create a type mirror for a regular Map in order to use MapQueryResultAdapter. This
            // avoids code duplication as Immutable Map can be initialized by creating an immutable
            // copy of a regular map.
            val mapType = context.processingEnv.getDeclaredType(
                context.processingEnv.requireTypeElement(Map::class),
                keyTypeArg,
                valueTypeArg
            )

            val resultAdapter = findQueryResultAdapter(mapType, query, extras) ?: return null
            return ImmutableMapQueryResultAdapter(
                context = context,
                parsedQuery = query,
                keyTypeArg = keyTypeArg,
                valueTypeArg = valueTypeArg,
                resultAdapter = resultAdapter
            )
        } else if (typeMirror.isTypeOf(ImmutableSetMultimap::class) ||
            typeMirror.isTypeOf(ImmutableListMultimap::class) ||
            typeMirror.isTypeOf(ImmutableMultimap::class)
        ) {
            val keyTypeArg = typeMirror.typeArguments[0].extendsBoundOrSelf()
            val valueTypeArg = typeMirror.typeArguments[1].extendsBoundOrSelf()
            checkTypeNullability(typeMirror, extras)

            if (valueTypeArg.typeElement == null) {
                context.logger.e(
                    "Guava multimap 'value' type argument does not represent a class. " +
                        "Found $valueTypeArg."
                )
                return null
            }

            val immutableClassName = if (typeMirror.isTypeOf(ImmutableListMultimap::class)) {
                GuavaTypeNames.IMMUTABLE_LIST_MULTIMAP
            } else if (typeMirror.isTypeOf(ImmutableSetMultimap::class)) {
                GuavaTypeNames.IMMUTABLE_SET_MULTIMAP
            } else {
                // Return type is base class ImmutableMultimap which is not recommended.
                context.logger.e(DO_NOT_USE_GENERIC_IMMUTABLE_MULTIMAP)
                return null
            }

            // Get @MapInfo info if any (this might be null)
            val mapInfo = extras.getData(MapInfo::class)
            val keyRowAdapter = findRowAdapter(
                typeMirror = keyTypeArg,
                query = query,
                columnName = mapInfo?.keyColumnName
            ) ?: return null

            val valueRowAdapter = findRowAdapter(
                typeMirror = valueTypeArg,
                query = query,
                columnName = mapInfo?.valueColumnName
            ) ?: return null

            validateMapTypeArgs(
                context = context,
                keyTypeArg = keyTypeArg,
                valueTypeArg = valueTypeArg,
                keyReader = findCursorValueReader(keyTypeArg, null),
                valueReader = findCursorValueReader(valueTypeArg, null),
                mapInfo = mapInfo
            )
            return GuavaImmutableMultimapQueryResultAdapter(
                context = context,
                parsedQuery = query,
                keyTypeArg = keyTypeArg,
                valueTypeArg = valueTypeArg,
                keyRowAdapter = checkTypeOrNull(keyRowAdapter) ?: return null,
                valueRowAdapter = checkTypeOrNull(valueRowAdapter) ?: return null,
                immutableClassName = immutableClassName
            )
        } else if (typeMirror.isTypeOf(java.util.Map::class) ||
            typeMirror.rawType.asTypeName().equalsIgnoreNullability(ARRAY_MAP) ||
            typeMirror.rawType.asTypeName().equalsIgnoreNullability(LONG_SPARSE_ARRAY) ||
            typeMirror.rawType.asTypeName().equalsIgnoreNullability(INT_SPARSE_ARRAY)
        ) {
            val mapType = when (typeMirror.rawType.asTypeName()) {
                LONG_SPARSE_ARRAY -> MultimapQueryResultAdapter.MapType.LONG_SPARSE
                INT_SPARSE_ARRAY -> MultimapQueryResultAdapter.MapType.INT_SPARSE
                ARRAY_MAP -> MultimapQueryResultAdapter.MapType.ARRAY_MAP
                else -> MultimapQueryResultAdapter.MapType.DEFAULT
            }
            val keyTypeArg = when (mapType) {
                MultimapQueryResultAdapter.MapType.LONG_SPARSE ->
                    context.processingEnv.requireType(XTypeName.PRIMITIVE_LONG)
                MultimapQueryResultAdapter.MapType.INT_SPARSE ->
                    context.processingEnv.requireType(XTypeName.PRIMITIVE_INT)
                else ->
                    typeMirror.typeArguments[0].extendsBoundOrSelf()
            }
            checkTypeNullability(typeMirror, extras)

            val mapValueTypeArg = if (mapType.isSparseArray()) {
                typeMirror.typeArguments[0].extendsBoundOrSelf()
            } else {
                typeMirror.typeArguments[1].extendsBoundOrSelf()
            }

            if (mapValueTypeArg.typeElement == null) {
                context.logger.e(
                    "Multimap 'value' collection type argument does not represent a class. " +
                        "Found $mapValueTypeArg."
                )
                return null
            }
            // TODO: Handle nested collection values in the map

            // Get @MapInfo info if any (this might be null)
            val mapInfo = extras.getData(MapInfo::class)
            val collectionTypeRaw = context.COMMON_TYPES.READONLY_COLLECTION.rawType
            if (collectionTypeRaw.isAssignableFrom(mapValueTypeArg.rawType)) {
                // The Map's value type argument is assignable to a Collection, we need to make
                // sure it is either a list or a set.
                val listTypeRaw = context.COMMON_TYPES.LIST.rawType
                val setTypeRaw = context.COMMON_TYPES.SET.rawType
                val collectionValueType = when {
                    mapValueTypeArg.rawType.isAssignableFrom(listTypeRaw) ->
                        MultimapQueryResultAdapter.CollectionValueType.LIST
                    mapValueTypeArg.rawType.isAssignableFrom(setTypeRaw) ->
                        MultimapQueryResultAdapter.CollectionValueType.SET
                    else -> {
                        context.logger.e(
                            ProcessorErrors.valueCollectionMustBeListOrSet(
                                mapValueTypeArg.asTypeName().toString(context.codeLanguage)
                            )
                        )
                        return null
                    }
                }

                val valueTypeArg = mapValueTypeArg.typeArguments.single().extendsBoundOrSelf()

                val keyRowAdapter = findRowAdapter(
                    typeMirror = keyTypeArg,
                    query = query,
                    columnName = mapInfo?.keyColumnName
                ) ?: return null

                val valueRowAdapter = findRowAdapter(
                    typeMirror = valueTypeArg,
                    query = query,
                    columnName = mapInfo?.valueColumnName
                ) ?: return null

                validateMapTypeArgs(
                    context = context,
                    keyTypeArg = keyTypeArg,
                    valueTypeArg = valueTypeArg,
                    keyReader = findCursorValueReader(keyTypeArg, null),
                    valueReader = findCursorValueReader(valueTypeArg, null),
                    mapInfo = mapInfo
                )
                return MapQueryResultAdapter(
                    context = context,
                    parsedQuery = query,
                    keyTypeArg = keyTypeArg,
                    valueTypeArg = valueTypeArg,
                    keyRowAdapter = checkTypeOrNull(keyRowAdapter) ?: return null,
                    valueRowAdapter = checkTypeOrNull(valueRowAdapter) ?: return null,
                    valueCollectionType = collectionValueType,
                    mapType = mapType
                )
            } else {
                val keyRowAdapter = findRowAdapter(
                    typeMirror = keyTypeArg,
                    query = query,
                    columnName = mapInfo?.keyColumnName
                ) ?: return null
                val valueRowAdapter = findRowAdapter(
                    typeMirror = mapValueTypeArg,
                    query = query,
                    columnName = mapInfo?.valueColumnName
                ) ?: return null

                validateMapTypeArgs(
                    context = context,
                    keyTypeArg = keyTypeArg,
                    valueTypeArg = mapValueTypeArg,
                    keyReader = findCursorValueReader(keyTypeArg, null),
                    valueReader = findCursorValueReader(mapValueTypeArg, null),
                    mapInfo = mapInfo
                )
                return MapQueryResultAdapter(
                    context = context,
                    parsedQuery = query,
                    keyTypeArg = keyTypeArg,
                    valueTypeArg = mapValueTypeArg,
                    keyRowAdapter = checkTypeOrNull(keyRowAdapter) ?: return null,
                    valueRowAdapter = checkTypeOrNull(valueRowAdapter) ?: return null,
                    valueCollectionType = null,
                    mapType = mapType
                )
            }
        }
        return null
    }

    private fun checkTypeNullability(
        searchingType: XType,
        extras: TypeAdapterExtras,
        typeKeyword: String = "Collection",
        arrayComponentType: XType? = null
    ) {
        if (context.codeLanguage != CodeLanguage.KOTLIN) {
            return
        }

        val collectionType: XType = extras.getData(
            ObservableQueryResultBinderProvider.OriginalTypeArg::class
        )?.original ?: searchingType

        if (collectionType.nullability != XNullability.NONNULL) {
            context.logger.w(
                Warning.UNNECESSARY_NULLABILITY_IN_DAO_RETURN_TYPE,
                ProcessorErrors.nullableCollectionOrArrayReturnTypeInDaoMethod(
                    searchingType.asTypeName().toString(context.codeLanguage),
                    typeKeyword
                )
            )
        }

        // Since Array has typeArg in the componentType and not typeArguments, need a special check.
        if (arrayComponentType != null && arrayComponentType.nullability != XNullability.NONNULL) {
            context.logger.w(
                Warning.UNNECESSARY_NULLABILITY_IN_DAO_RETURN_TYPE,
                ProcessorErrors.nullableComponentInDaoMethodReturnType(
                    searchingType.asTypeName().toString(context.codeLanguage)
                )
            )
            return
        }

        collectionType.typeArguments.forEach { typeArg ->
            if (typeArg.nullability != XNullability.NONNULL) {
                context.logger.w(
                    Warning.UNNECESSARY_NULLABILITY_IN_DAO_RETURN_TYPE,
                    ProcessorErrors.nullableComponentInDaoMethodReturnType(
                        searchingType.asTypeName().toString(context.codeLanguage)
                    )
                )
            }
        }
    }

    /**
     * Find a converter from cursor to the given type mirror.
     * If there is information about the query result, we try to use it to accept *any* POJO.
     */
    fun findRowAdapter(
        typeMirror: XType,
        query: ParsedQuery,
        columnName: String? = null
    ): RowAdapter? {
        if (typeMirror.isError()) {
            return null
        }

        val typeElement = typeMirror.typeElement
        if (typeElement != null && !typeMirror.asTypeName().isPrimitive) {
            if (typeMirror.typeArguments.isNotEmpty()) {
                // TODO one day support this
                return null
            }
            val resultInfo = query.resultInfo

            val (rowAdapter, rowAdapterLogs) = if (resultInfo != null && query.errors.isEmpty() &&
                resultInfo.error == null
            ) {
                // if result info is not null, first try a pojo row adapter
                context.collectLogs { subContext ->
                    val pojo = PojoProcessor.createFor(
                        context = subContext,
                        element = typeElement,
                        bindingScope = FieldProcessor.BindingScope.READ_FROM_CURSOR,
                        parent = null
                    ).process()
                    PojoRowAdapter(
                        context = subContext,
                        info = resultInfo,
                        query = query,
                        pojo = pojo,
                        out = typeMirror
                    )
                }
            } else {
                Pair(null, null)
            }

            if (rowAdapter == null && query.resultInfo == null) {
                // we don't know what query returns. Check for entity.
                if (typeElement.isEntityElement()) {
                    return EntityRowAdapter(
                        EntityProcessor(
                            context = context,
                            element = typeElement
                        ).process()
                    )
                }
            }

            if (rowAdapter != null && rowAdapterLogs?.hasErrors() != true) {
                rowAdapterLogs?.writeTo(context)
                return rowAdapter
            }

            if (columnName != null) {
                val singleNamedColumn = findCursorValueReader(
                    typeMirror,
                    query.resultInfo?.columns?.find {
                        it.name == columnName
                    }?.type
                )
                if (singleNamedColumn != null) {
                    return SingleNamedColumnRowAdapter(singleNamedColumn, columnName)
                }
            }

            if ((resultInfo?.columns?.size ?: 1) == 1) {
                val singleColumn = findCursorValueReader(
                    typeMirror,
                    resultInfo?.columns?.get(0)?.type
                )
                if (singleColumn != null) {
                    return SingleColumnRowAdapter(singleColumn)
                }
            }
            // if we tried, return its errors
            if (rowAdapter != null) {
                rowAdapterLogs?.writeTo(context)
                return rowAdapter
            }

            // use pojo adapter as a last resort.
            // this happens when @RawQuery or @SkipVerification is used.
            if (query.resultInfo == null &&
                typeMirror.isNotVoid() &&
                typeMirror.isNotVoidObject() &&
                typeMirror.isNotKotlinUnit()
            ) {
                val pojo = PojoProcessor.createFor(
                    context = context,
                    element = typeElement,
                    bindingScope = FieldProcessor.BindingScope.READ_FROM_CURSOR,
                    parent = null
                ).process()
                return PojoRowAdapter(
                    context = context,
                    info = null,
                    query = query,
                    pojo = pojo,
                    out = typeMirror
                )
            }
            return null
        } else {
            if (columnName != null) {
                val singleNamedColumn = findCursorValueReader(
                    typeMirror,
                    query.resultInfo?.columns?.find { it.name == columnName }?.type
                )
                if (singleNamedColumn != null) {
                    return SingleNamedColumnRowAdapter(singleNamedColumn, columnName)
                }
            }
            val singleColumn = findCursorValueReader(typeMirror, null) ?: return null
            return SingleColumnRowAdapter(singleColumn)
        }
    }

    fun findQueryParameterAdapter(
        typeMirror: XType,
        isMultipleParameter: Boolean
    ): QueryParameterAdapter? {
        if (context.COMMON_TYPES.READONLY_COLLECTION.rawType.isAssignableFrom(typeMirror)) {
            val typeArg = typeMirror.typeArguments.first().extendsBoundOrSelf()
            // An adapter for the collection type arg wrapped in the built-in collection adapter.
            val wrappedCollectionAdapter = findStatementValueBinder(typeArg, null)?.let {
                CollectionQueryParameterAdapter(it, typeMirror.nullability)
            }
            // An adapter for the collection itself, likely a user provided type converter for the
            // collection.
            val directCollectionAdapter = findStatementValueBinder(typeMirror, null)?.let {
                BasicQueryParameterAdapter(it)
            }
            // Prioritize built-in collection adapters when finding an adapter for a multi-value
            // binding param since it is likely wrong to use a collection to single value converter
            // for an expression that takes in multiple values.
            return if (isMultipleParameter) {
                wrappedCollectionAdapter ?: directCollectionAdapter
            } else {
                directCollectionAdapter ?: wrappedCollectionAdapter
            }
        } else if (typeMirror.isArray() && typeMirror.componentType.isNotByte()) {
            val component = typeMirror.componentType
            val binder = findStatementValueBinder(component, null) ?: return null
            return ArrayQueryParameterAdapter(binder, typeMirror.nullability)
        } else {
            val binder = findStatementValueBinder(typeMirror, null) ?: return null
            return BasicQueryParameterAdapter(binder)
        }
    }

    private fun getAllColumnAdapters(input: XType): List<ColumnTypeAdapter> {
        return columnTypeAdapters.filter { input.isSameType(it.out) }
    }
}
