package com.ustadmobile.core.db.dao

import androidx.paging.PagingSource
import com.ustadmobile.door.ext.doorPrimaryKeyManager
import com.ustadmobile.door.ext.rootDatabase
import com.ustadmobile.door.room.RoomDatabase
import com.ustadmobile.door.util.systemTimeInMillis
import com.ustadmobile.lib.db.composites.ContentEntryAndDetail
import com.ustadmobile.lib.db.composites.ContentEntryAndLanguage
import com.ustadmobile.lib.db.composites.ContentEntryAndListDetail
import com.ustadmobile.lib.db.composites.ContentEntryAndPicture
import com.ustadmobile.lib.db.entities.ContentEntry
import com.ustadmobile.lib.db.entities.ContentEntryWithLanguage
import com.ustadmobile.lib.db.entities.UidAndLabel
import kotlin.Boolean
import kotlin.IllegalStateException
import kotlin.Int
import kotlin.Long
import kotlin.String
import kotlin.Unit
import kotlin.collections.List
import kotlinx.coroutines.flow.Flow

public class ContentEntryDao_DoorWrapper(
  private val _db: RoomDatabase,
  private val _dao: ContentEntryDao,
) : ContentEntryDao() {
  override suspend fun insertListAsync(entityList: List<ContentEntry>) {
    val _pkManager = _db.rootDatabase.doorPrimaryKeyManager
    val _generatedPks = mutableListOf<Long>()
    entityList.iterator().forEach  {
      if(it.contentEntryUid == 0L) {
        val _newPk = _pkManager.nextIdAsync(42)
        it.contentEntryUid = _newPk
        _generatedPks += _newPk
      }
      it.contentEntryLct = systemTimeInMillis()
    }
    //must set versionid and/or primary key here
    _dao.insertListAsync(entityList)
  }

  override suspend fun upsertAsync(entity: ContentEntry) {
    val _pkManager = _db.rootDatabase.doorPrimaryKeyManager
    if(entity.contentEntryUid == 0L) {
      val _newPk = _pkManager.nextIdAsync(42)
      entity.contentEntryUid = _newPk
    }
    entity.contentEntryLct = systemTimeInMillis()
    //must set versionid and/or primary key here
    _dao.upsertAsync(entity)
  }

  override suspend fun findByUidAsync(entryUid: Long): ContentEntry? = _dao.findByUidAsync(entryUid)

  override suspend fun findEntryWithLanguageByEntryIdAsync(entryUuid: Long):
      ContentEntryAndLanguage? = _dao.findEntryWithLanguageByEntryIdAsync(entryUuid)

  override suspend fun findByUidWithEditDetails(uid: Long): ContentEntryAndPicture? =
      _dao.findByUidWithEditDetails(uid)

  override fun findByContentEntryUidWithDetailsAsFlow(
    contentEntryUid: Long,
    clazzUid: Long,
    courseBlockUid: Long,
    accountPersonUid: Long,
  ): Flow<ContentEntryAndDetail?> = _dao.findByContentEntryUidWithDetailsAsFlow(contentEntryUid,
      clazzUid, courseBlockUid, accountPersonUid)

  override fun findBySourceUrl(sourceUrl: String): ContentEntry? = throw
      IllegalStateException("findBySourceUrl: synchronous db access is NOT possible on Javascript!")

  override suspend fun findTitleByUidAsync(entryUid: Long): String? =
      _dao.findTitleByUidAsync(entryUid)

  override fun getChildrenByParentUid(parentUid: Long): PagingSource<Int, ContentEntry> =
      _dao.getChildrenByParentUid(parentUid)

  override suspend fun getChildrenByParentAsync(parentUid: Long): List<ContentEntry> =
      _dao.getChildrenByParentAsync(parentUid)

  override suspend fun getCountNumberOfChildrenByParentUUidAsync(parentUid: Long): Int =
      _dao.getCountNumberOfChildrenByParentUUidAsync(parentUid)

  override suspend fun getContentByUuidAsync(parentUid: Long): ContentEntry? =
      _dao.getContentByUuidAsync(parentUid)

  override suspend fun findAllLanguageRelatedEntriesAsync(entryUuid: Long): List<ContentEntry> =
      _dao.findAllLanguageRelatedEntriesAsync(entryUuid)

  override fun update(entity: ContentEntry): Unit = throw
      IllegalStateException("update: synchronous db access is NOT possible on Javascript!")

  override suspend fun findByUidWithLanguageAsync(uid: Long): ContentEntryWithLanguage? =
      _dao.findByUidWithLanguageAsync(uid)

  override fun findByUid(entryUid: Long): ContentEntry? = throw
      IllegalStateException("findByUid: synchronous db access is NOT possible on Javascript!")

  override fun findByTitle(title: String): Flow<ContentEntry?> = _dao.findByTitle(title)

  override suspend fun findBySourceUrlWithContentEntryStatusAsync(sourceUrl: String): ContentEntry?
      = _dao.findBySourceUrlWithContentEntryStatusAsync(sourceUrl)

  override fun getChildrenByParentUidWithCategoryFilterOrderByName(
    accountPersonUid: Long,
    parentUid: Long,
    langParam: Long,
    categoryParam0: Long,
    sortOrder: Int,
    includeDeleted: Boolean,
  ): PagingSource<Int, ContentEntryAndListDetail> =
      _dao.getChildrenByParentUidWithCategoryFilterOrderByName(accountPersonUid, parentUid,
      langParam, categoryParam0, sortOrder, includeDeleted)

  override fun getContentFromMyCourses(accountPersonUid: Long):
      PagingSource<Int, ContentEntryAndListDetail> = _dao.getContentFromMyCourses(accountPersonUid)

  override fun getContentByOwner(accountPersonUid: Long):
      PagingSource<Int, ContentEntryAndListDetail> = _dao.getContentByOwner(accountPersonUid)

  override suspend fun updateAsync(entity: ContentEntry): Int {
    entity.contentEntryLct = systemTimeInMillis()
    //must set versionid and/or primary key here
    return _dao.updateAsync(entity)
  }

  override fun getChildrenByAll(parentUid: Long): List<ContentEntry> = throw
      IllegalStateException("getChildrenByAll: synchronous db access is NOT possible on Javascript!")

  override fun findLiveContentEntry(parentUid: Long): Flow<ContentEntry?> =
      _dao.findLiveContentEntry(parentUid)

  override fun getContentEntryUidFromXapiObjectId(objectId: String): Long = throw
      IllegalStateException("getContentEntryUidFromXapiObjectId: synchronous db access is NOT possible on Javascript!")

  override fun findSimilarIdEntryForKhan(sourceUrl: String): List<ContentEntry> = throw
      IllegalStateException("findSimilarIdEntryForKhan: synchronous db access is NOT possible on Javascript!")

  override fun updateContentEntryInActive(
    contentEntryUid: Long,
    ceInactive: Boolean,
    changedTime: Long,
  ): Unit = throw
      IllegalStateException("updateContentEntryInActive: synchronous db access is NOT possible on Javascript!")

  override fun updateContentEntryContentFlag(
    contentFlag: Int,
    contentEntryUid: Long,
    changedTime: Long,
  ): Unit = throw
      IllegalStateException("updateContentEntryContentFlag: synchronous db access is NOT possible on Javascript!")

  override suspend fun getContentEntryFromUids(contentEntryUids: List<Long>): List<UidAndLabel> =
      _dao.getContentEntryFromUids(contentEntryUids)

  public override fun insert(entity: ContentEntry): Long = throw
      IllegalStateException("insert: synchronous db access is NOT possible on Javascript!")

  public override suspend fun insertAsync(entity: ContentEntry): Long {
    val _pkManager = _db.rootDatabase.doorPrimaryKeyManager
    if(entity.contentEntryUid == 0L) {
      val _newPk = _pkManager.nextIdAsync(42)
      entity.contentEntryUid = _newPk
    }
    entity.contentEntryLct = systemTimeInMillis()
    //must set versionid and/or primary key here
    _dao.insertAsync(entity)
    return entity.contentEntryUid
  }

  public override fun insertList(entityList: List<ContentEntry>): Unit = throw
      IllegalStateException("insertList: synchronous db access is NOT possible on Javascript!")
}
