package com.rosetta.messenger.domain.chats.usecase

import com.rosetta.messenger.di.ProtocolGateway
import com.rosetta.messenger.network.AttachmentType
import com.rosetta.messenger.network.MessageAttachment
import com.rosetta.messenger.network.PacketMessage
import org.json.JSONArray
import org.json.JSONObject
import javax.inject.Inject

data class ForwardPayloadMessage(
    val messageId: String,
    val senderPublicKey: String,
    val senderName: String,
    val text: String,
    val timestamp: Long,
    val chachaKeyPlain: String,
    val attachments: List<MessageAttachment>
)

class SendForwardUseCase @Inject constructor(
    private val protocolGateway: ProtocolGateway
) {
    fun buildForwardReplyJson(
        messages: List<ForwardPayloadMessage>,
        rewrittenAttachments: Map<String, MessageAttachment>,
        rewrittenMessageIds: Set<String>,
        outgoingForwardPlainKeyHex: String,
        includeLocalUri: Boolean,
        rewriteKey: (messageId: String, attachmentId: String) -> String
    ): JSONArray {
        val replyJsonArray = JSONArray()
        messages.forEach { message ->
            val attachmentsArray = JSONArray()
            message.attachments.forEach { attachment ->
                val rewritten =
                    rewrittenAttachments[rewriteKey(message.messageId, attachment.id)]
                val effectiveAttachment = rewritten ?: attachment
                attachmentsArray.put(
                    JSONObject().apply {
                        put("id", effectiveAttachment.id)
                        put("type", effectiveAttachment.type.value)
                        put("preview", effectiveAttachment.preview)
                        put("width", effectiveAttachment.width)
                        put("height", effectiveAttachment.height)
                        put("blob", "")
                        put("transportTag", effectiveAttachment.transportTag)
                        put("transportServer", effectiveAttachment.transportServer)
                        put(
                            "transport",
                            JSONObject().apply {
                                put("transport_tag", effectiveAttachment.transportTag)
                                put("transport_server", effectiveAttachment.transportServer)
                            }
                        )
                        if (includeLocalUri && effectiveAttachment.localUri.isNotEmpty()) {
                            put("localUri", effectiveAttachment.localUri)
                        }
                    }
                )
            }

            val effectiveForwardPlainKey =
                if (message.messageId in rewrittenMessageIds && outgoingForwardPlainKeyHex.isNotEmpty()) {
                    outgoingForwardPlainKeyHex
                } else {
                    message.chachaKeyPlain
                }

            replyJsonArray.put(
                JSONObject().apply {
                    put("message_id", message.messageId)
                    put("publicKey", message.senderPublicKey)
                    put("message", message.text)
                    put("timestamp", message.timestamp)
                    put("attachments", attachmentsArray)
                    put("forwarded", true)
                    put("senderName", message.senderName)
                    if (effectiveForwardPlainKey.isNotEmpty()) {
                        put("chacha_key_plain", effectiveForwardPlainKey)
                    }
                }
            )
        }
        return replyJsonArray
    }

    fun buildForwardAttachment(
        replyAttachmentId: String,
        encryptedReplyBlob: String
    ): MessageAttachment =
        MessageAttachment(
            id = replyAttachmentId,
            blob = encryptedReplyBlob,
            type = AttachmentType.MESSAGES,
            preview = ""
        )

    fun dispatch(packet: PacketMessage, isSavedMessages: Boolean) {
        if (!isSavedMessages) {
            protocolGateway.sendMessageWithRetry(packet)
        }
    }
}
