/*
 * Copyright © All Contributors. See LICENSE and AUTHORS in the root directory for details.
 */

package at.bitfire.davdroid.sync

import android.accounts.Account
import android.content.ContentProviderClient
import at.bitfire.davdroid.db.Collection
import at.bitfire.davdroid.db.Service
import at.bitfire.davdroid.resource.LocalCalendar
import at.bitfire.davdroid.resource.LocalCalendarStore
import at.bitfire.davdroid.settings.AccountSettings
import at.bitfire.synctools.storage.calendar.AndroidCalendarProvider
import dagger.assisted.Assisted
import dagger.assisted.AssistedFactory
import dagger.assisted.AssistedInject
import java.util.logging.Level

/**
 * Sync logic for calendars
 */
class CalendarSyncer @AssistedInject constructor(
    @Assisted account: Account,
    @Assisted resync: ResyncType?,
    @Assisted syncResult: SyncResult,
    calendarStore: LocalCalendarStore,
    private val accountSettingsFactory: AccountSettings.Factory,
    private val calendarSyncManagerFactory: CalendarSyncManager.Factory
): Syncer<LocalCalendarStore, LocalCalendar>(account, resync, syncResult) {

    @AssistedFactory
    interface Factory {
        fun create(account: Account, resyncType: ResyncType?, syncResult: SyncResult): CalendarSyncer
    }

    override val dataStore = calendarStore

    override val serviceType: String
        get() = Service.TYPE_CALDAV


    override fun prepare(provider: ContentProviderClient): Boolean {
        // Update colors
        val accountSettings = accountSettingsFactory.create(account)

        val calendarProvider = AndroidCalendarProvider(account, provider)
        if (accountSettings.getEventColors())
            calendarProvider.provideCss3ColorIndices()
        else
            calendarProvider.removeColorIndices()
        return true
    }

    override fun getDbSyncCollections(serviceId: Long): List<Collection> =
        collectionRepository.getSyncCalendars(serviceId)

    override suspend fun syncCollection(
        provider: ContentProviderClient,
        localCollection: LocalCalendar,
        remoteCollection: Collection
    ) {
        logger.log(
            Level.INFO,
            "Synchronizing calendar #{0}, DB Collection ID: {1}, URL: {2}",
            arrayOf<Any?>(
                localCollection.androidCalendar.id,
                localCollection.dbCollectionId,
                localCollection.androidCalendar.name
            )
        )

        val syncManager = calendarSyncManagerFactory.calendarSyncManager(
            account,
            httpClient,
            syncResult,
            localCollection,
            remoteCollection,
            resync
        )
        syncManager.performSync()
    }

}