import ComposableArchitecture
import Foundation

/*
 Flat context structure that gets sent with user events,
 not playback events.
 */
public struct AnalyticsContext: Codable {
    public let contextType: String
    public let contextId: String?

    // When navigating from a deeplink
    public let sourceUrl: String?

    // When navigating from a clip
    public var clipId: String?

    public var hookId: String?

    // When tapping to view a profile
    public var authorHandle: String?
    public var profileUserId: String?

    public var recommendationItemId: String?

    public var navigationIntent: String?

    public var targetCommentId: String?

    public init(
        recommendationItemId: String? = nil,
        contextType: String?,
        contextId: String?,
        sourceUrl: String? = nil,
        clipId: String? = nil,
        hookId: String? = nil,
        authorHandle: String? = nil,
        profileUserId: String? = nil,
        navigationIntent: String? = nil,
        targetCommentId: String? = nil
    ) {
        self.recommendationItemId = recommendationItemId
        self.contextType = contextType ?? "unknown"
        self.contextId = contextId
        self.sourceUrl = sourceUrl
        self.clipId = clipId
        self.hookId = hookId
        self.authorHandle = authorHandle
        self.profileUserId = profileUserId
        self.navigationIntent = navigationIntent
        self.targetCommentId = targetCommentId
    }

    public init(
        source: ContextSource,
        sourceUrl: String? = nil,
        clipId: String? = nil,
        hookId: String? = nil,
        authorHandle: String? = nil,
        profileUserId: String? = nil,
        recommendationItemId: String? = nil,
        navigationIntent: String? = nil,
        targetCommentId: String? = nil
    ) {
        self.contextType = source.analyticsContext.contextType
        self.contextId = source.analyticsContext.contextId
        self.sourceUrl = sourceUrl
        self.clipId = clipId
        self.hookId = hookId
        self.authorHandle = authorHandle
        self.profileUserId = profileUserId
        self.recommendationItemId = recommendationItemId
        self.navigationIntent = navigationIntent
        self.targetCommentId = targetCommentId
    }

    public func toJsonString() -> String {
        guard let data = try? JSONEncoder().encode(self),
              let jsonString = String(data: data, encoding: .utf8)
        else {
            return "{}"
        }
        return jsonString
    }
}

public extension AnalyticsContext {
    static func mapContextType(_ originalType: String?) -> String {
        guard let originalType = originalType else { return "unknown" }

        switch originalType.lowercased() {
        case "hooks_feed":
            return "hooks_feed"
        case "profile":
            return "profile"
        case "library":
            return "library"
        case "profile_grid":
            return "profile_grid"
        case "library_grid":
            return "library_grid"
        case "hook":
            return "hook"
        case "notification":
            return "notification"
        case "clip":
            return "clip"
        default:
            return "unknown"
        }
    }
}
