import PRESTOplay

// MARK: - PrestoPlayError

@objc(PrestoPlayError)
public class PrestoPlayError: NSObject, Codable, Error {
    let code: ErrorCode
    let severity: ErrorSeverity
    let message: String?
    let causeMessage: String?
    let metadata: ErrorMetadata?
    var nativeError: NativeError?

    public init(
        _ severity: ErrorSeverity,
        _ code: ErrorCode,
        message: String? = nil,
        causeMessage: String? = nil,
        metadata: ErrorMetadata? = nil
    ) {
        self.code = code
        self.severity = severity
        self.message = message
        self.causeMessage = causeMessage
        self.metadata = metadata
        self.nativeError = nil
    }

    public convenience init(_ error: PRESTOerror) {
                
        let severity: ErrorSeverity = {
            switch error.severity {
            case .fatal:
                return .fatal
            default:
                return .recoverable
            }
        }()

        let code: ErrorCode = {
            switch error.type {
            case .downloader_id_already_in_use:
                return .downloadIdAlreadyInUse
            case .downloader_id_not_found:
                return .downloadNotFound
            case .downloader_no_content_to_be_removed,
                 .downloader_not_available_for_this_format,
                 .downloader_request_creation_failed,
                 .downloader_asset_tracks_cannot_be_loaded,
                 .downloader_media_selection_cannot_be_loaded,
                 .downloader_offline_key_not_retrieved,
                 .downloader_cellular_access_disallowed:
                return .downloadFailed
            case .network_request_cancelled,
                 .network_error,
                 .network_http_bad_status_code,
                 .player_resource_unavailable:
                return .mediaDownloadingFailed
            case .system_internet_connection_unavailable:
                return .connectivityLost
            case .system_internet_connection_available:
                return .connectivityGained
            case .player_avplayer_stall:
                return .timeoutOccurred
            case .text_content_invalid:
                return .textUnsupported
            case .text_track_already_loaded:
                return .textTrackAlreadyLoaded
            case .hls_playlist_invalid:
                return .manifestParsingFailed
            case .player_open_error:
                return .streamLoadingFailed
            case .drm_fairplay_key_error,
                 .drm_acquisition_terminated,
                 .drm_malformed_request,
                 .drm_missing_key_uri,
                 .drm_missing_licensing_url,
                 .drm_local_internal_error,
                 .drm_server_internal_error,
                 .drm_server_licensing_error,
                 .drm_today:
                return .drmError
            case .drm_unsupported_system:
                return .drmUnsupported
            case .drm_second_screen_detected,
                 .drm_screen_recording_detected:
                return .secondaryDisplayForbidden
            case .drm_license_expired:
                return .keyExpired
            case .system,
                 .player_avplayer_error:
                return .playerError
            case .thumbnails_content_invalid:
                return .thumbnailsContentInvalid
            case .thumbnails_image_missing:
                return .thumbnailsImageMissing
            case .ads_error:
                return .adError
            case .storage_error_while_removing_file:
                return .storageRemovingFailed
            case .storage_error_reading:
                return .storageReadingFailed
            case .storage_error_writing:
                return .storageWritingFailed
            case .sdk_license_invalid:
                return .sdkInvalidLicense
            default:
                return .playerError
            }
        }()

        self.init(
            severity,
            code,
            message: error.message,
            causeMessage: error.parentError?.localizedDescription,
            metadata: ErrorMetadata(
                url: error.data["url"],
                httpStatusCode: Int(error.data["httpCode"] ?? ""),
                httpResponseBody: error.data["responseBody"]
            )
        )
        
        self.nativeError = NativeError(error);

    }
}
