package com.seven.ikar.kotlin.feature.chatinfo

import androidx.lifecycle.ViewModel
import androidx.lifecycle.viewModelScope
import com.seven.ikar.kotlin.app.AppContainer
import com.seven.ikar.kotlin.core.model.ChatInfoDto
import com.seven.ikar.kotlin.core.model.ChatInviteLinkDto
import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.flow.StateFlow
import kotlinx.coroutines.flow.asStateFlow
import kotlinx.coroutines.launch

data class ChatInfoUiState(
    val info: ChatInfoDto? = null,
    val inviteTitle: String = "",
    val inviteCreatesJoinRequest: Boolean = false,
    val topicTitle: String = "",
    val isLoading: Boolean = false,
    val isSaving: Boolean = false,
    val errorMessage: String? = null
)

class ChatInfoViewModel(
    private val container: AppContainer,
    private val chatId: String
) : ViewModel() {
    private val _uiState = MutableStateFlow(ChatInfoUiState())
    val uiState: StateFlow<ChatInfoUiState> = _uiState.asStateFlow()

    init {
        refresh()
    }

    fun refresh() {
        viewModelScope.launch {
            _uiState.value = _uiState.value.copy(isLoading = true, errorMessage = null)
            runCatching {
                container.executeAuthorized { session ->
                    container.apiClient.getChatInfo(session.accessToken, chatId)
                }
            }.onSuccess { info ->
                _uiState.value = _uiState.value.copy(info = info, isLoading = false)
            }.onFailure { error ->
                _uiState.value = _uiState.value.copy(isLoading = false, errorMessage = error.message)
            }
        }
    }

    fun updateInviteTitle(value: String) {
        _uiState.value = _uiState.value.copy(inviteTitle = value.take(64))
    }

    fun updateInviteCreatesJoinRequest(value: Boolean) {
        _uiState.value = _uiState.value.copy(inviteCreatesJoinRequest = value)
    }

    fun updateTopicTitle(value: String) {
        _uiState.value = _uiState.value.copy(topicTitle = value.take(80))
    }

    fun createInviteLink() {
        val state = _uiState.value
        if (state.isSaving) return
        viewModelScope.launch {
            _uiState.value = _uiState.value.copy(isSaving = true, errorMessage = null)
            runCatching {
                container.executeAuthorized { session ->
                    container.apiClient.createChatInviteLink(
                        accessToken = session.accessToken,
                        chatId = chatId,
                        title = state.inviteTitle,
                        createsJoinRequest = state.inviteCreatesJoinRequest
                    )
                }
            }.onSuccess {
                _uiState.value = _uiState.value.copy(
                    inviteTitle = "",
                    inviteCreatesJoinRequest = false,
                    isSaving = false
                )
                refresh()
            }.onFailure { error ->
                _uiState.value = _uiState.value.copy(isSaving = false, errorMessage = error.message)
            }
        }
    }

    fun revokeInviteLink(link: ChatInviteLinkDto) {
        if (_uiState.value.isSaving) return
        viewModelScope.launch {
            _uiState.value = _uiState.value.copy(isSaving = true, errorMessage = null)
            runCatching {
                container.executeAuthorized { session ->
                    container.apiClient.revokeChatInviteLink(session.accessToken, chatId, link.id)
                }
            }.onSuccess {
                _uiState.value = _uiState.value.copy(isSaving = false)
                refresh()
            }.onFailure { error ->
                _uiState.value = _uiState.value.copy(isSaving = false, errorMessage = error.message)
            }
        }
    }

    fun createTopic() {
        val state = _uiState.value
        val title = state.topicTitle.trim()
        if (state.isSaving || title.length < 2) return
        viewModelScope.launch {
            _uiState.value = _uiState.value.copy(isSaving = true, errorMessage = null)
            runCatching {
                container.executeAuthorized { session ->
                    container.apiClient.createChatTopic(session.accessToken, chatId, title)
                }
            }.onSuccess {
                _uiState.value = _uiState.value.copy(topicTitle = "", isSaving = false)
                refresh()
            }.onFailure { error ->
                _uiState.value = _uiState.value.copy(isSaving = false, errorMessage = error.message)
            }
        }
    }
}
