package com.rssuper.models

import com.squareup.moshi.Moshi
import com.squareup.moshi.kotlin.reflect.KotlinJsonAdapterFactory
import org.junit.Assert.assertEquals
import org.junit.Assert.assertNotNull
import org.junit.Assert.assertNull
import org.junit.Assert.assertTrue
import org.junit.Before
import org.junit.Test
import java.util.Date

class FeedTest {

    private lateinit var moshi: Moshi
    private lateinit var adapter: com.squareup.moshi.JsonAdapter<Feed>

    @Before
    fun setup() {
        moshi = Moshi.Builder()
            .add(KotlinJsonAdapterFactory())
            .build()
        adapter = moshi.adapter(Feed::class.java)
    }

    @Test
    fun testSerialization() {
        val feed = Feed(
            id = "feed-1",
            title = "Tech News",
            link = "https://example.com",
            description = "Technology news feed",
            subtitle = "Daily tech updates",
            language = "en",
            rawUrl = "https://example.com/feed.xml",
            ttl = 60,
            items = listOf(
                FeedItem(id = "item-1", title = "Article 1"),
                FeedItem(id = "item-2", title = "Article 2")
            )
        )

        val json = adapter.toJson(feed)
        assertNotNull(json)
    }

    @Test
    fun testDeserialization() {
        val json = """{
            "id": "feed-1",
            "title": "Tech News",
            "link": "https://example.com",
            "description": "Technology news feed",
            "subtitle": "Daily tech updates",
            "language": "en",
            "rawUrl": "https://example.com/feed.xml",
            "ttl": 60,
            "items": [
                {"id": "item-1", "title": "Article 1"},
                {"id": "item-2", "title": "Article 2"}
            ]
        }"""

        val feed = adapter.fromJson(json)
        assertNotNull(feed)
        assertEquals("feed-1", feed?.id)
        assertEquals("Tech News", feed?.title)
        assertEquals(2, feed?.items?.size)
    }

    @Test
    fun testOptionalFieldsNull() {
        val json = """{
            "id": "feed-1",
            "title": "Tech News",
            "rawUrl": "https://example.com/feed.xml"
        }"""

        val feed = adapter.fromJson(json)
        assertNotNull(feed)
        assertNull(feed?.link)
        assertNull(feed?.description)
        assertNull(feed?.language)
    }

    @Test
    fun testEmptyItemsList() {
        val json = """{
            "id": "feed-1",
            "title": "Tech News",
            "rawUrl": "https://example.com/feed.xml",
            "items": []
        }"""

        val feed = adapter.fromJson(json)
        assertNotNull(feed)
        assertTrue(feed?.items?.isEmpty() == true)
    }

    @Test
    fun testCopy() {
        val original = Feed(
            id = "feed-1",
            title = "Original Title",
            rawUrl = "https://example.com/feed.xml"
        )

        val modified = original.copy(title = "Modified Title")

        assertEquals("feed-1", modified.id)
        assertEquals("Modified Title", modified.title)
        assertEquals("https://example.com/feed.xml", modified.rawUrl)
    }

    @Test
    fun testEqualsAndHashCode() {
        val feed1 = Feed(id = "feed-1", title = "Test", rawUrl = "https://example.com")
        val feed2 = Feed(id = "feed-1", title = "Test", rawUrl = "https://example.com")
        val feed3 = Feed(id = "feed-2", title = "Test", rawUrl = "https://example.com")

        assertEquals(feed1, feed2)
        assertEquals(feed1.hashCode(), feed2.hashCode())
        assert(feed1 != feed3)
    }

    @Test
    fun testToString() {
        val feed = Feed(
            id = "feed-1",
            title = "Tech News",
            rawUrl = "https://example.com/feed.xml"
        )

        val toString = feed.toString()
        assertNotNull(toString)
        assert(toString.contains("id=feed-1"))
        assert(toString.contains("title=Tech News"))
    }
}
