package com.za.service

import android.app.Notification
import android.app.NotificationChannel
import android.app.NotificationManager
import android.content.Context
import android.media.RingtoneManager
import android.os.Build
import androidx.core.app.NotificationCompat
import cn.jiguang.api.utils.JCollectionAuth
import cn.jpush.android.api.JPushInterface
import com.google.gson.Gson
import com.za.bean.JpushBean
import com.za.common.GlobalData
import com.za.common.log.LogUtil
import com.za.common.util.DeviceUtil
import com.za.service.mqtt.MyMqttClient
import com.za.servicing.R
import java.util.concurrent.atomic.AtomicReference

interface PushListener {
	fun newOrderMsg(jpushBean : JpushBean)
	fun giveUpOrder(jpushBean : JpushBean)
	fun revokeOrder(jpushBean : JpushBean)
	fun reDispatchOrder(jpushBean : JpushBean)
	fun broadcast(string : String)
	fun importantTip(jpushBean : JpushBean)
}

data class LastJPushBean(val msg : String, val time : Long = System.currentTimeMillis())

object ServiceManager {
	private val pushListener = AtomicReference<PushListener>()
	private var lastJPushBean : LastJPushBean? = null

	// Initialize SharedPreferences
	fun initialize(context : Context) {
		LogUtil.print("ServiceManager", "Initializing ServiceManager")
		jpushRegister(context)
		MyMqttClient.initialize(deviceId = DeviceUtil.getAndroidId(context))
	}

	// Register JPush
	private fun jpushRegister(context : Context) {
		try {
			JCollectionAuth.setAuth(context, true)
			JPushInterface.setDebugMode(false)
			JPushInterface.init(context)
			LogUtil.print("ServiceManager", "JPush initialized successfully")
		} catch (e : Exception) {
			LogUtil.print("ServiceManager", "JPush initialization failed: ${e.message}")
		}
	}

	// Register push listener
	fun registerPushListener(listener : PushListener?) {
		listener?.let {
			pushListener.set(it)
			LogUtil.print("ServiceManager", "Registered push listener: ${it.javaClass.simpleName}")
		}
	}

	// Handle incoming push messages
	fun handlerPushMsg(msg : String) {
		LogUtil.print("JpushMessage", "Received push message: $msg")
		if (msg.startsWith("broadcast:")) {
			handleBroadcast(msg)
			return
		}
		try {
			val jpushOrderInfoBean = Gson().fromJson(msg, JpushBean::class.java)
			if (lastJPushBean != null && (System.currentTimeMillis() - lastJPushBean !!.time < 3000) && lastJPushBean !!.msg == jpushOrderInfoBean.taskCode) {
				LogUtil.print("MessageHandler", "Duplicate message: " + lastJPushBean?.msg)
				return
			}

			jpushOrderInfoBean?.taskCode?.let {
				lastJPushBean = LastJPushBean(it)
			}
			sendSystemNotificationFromMessage(jpushOrderInfoBean)
			when (jpushOrderInfoBean.pushType) {
				0 -> newOrderMsg(jpushOrderInfoBean)
				1 -> handleTypeOneMessage(jpushOrderInfoBean)
				3 -> importantTip(jpushOrderInfoBean)
				else -> LogUtil.print("JpushMessage",
					"Unknown push type: ${jpushOrderInfoBean.pushType}")
			}
		} catch (e : Exception) {
			if (msg.startsWith("broadcast:")) {
				handleBroadcast(msg)
			}
			LogUtil.print("JpushMessage", "Error handling message: ${e.message}")
		}
	}

	// Handle broadcast messages
	private fun handleBroadcast(msg : String) {
		try {
			val content = msg.substring(10)
			pushListener.get()?.broadcast(content)
			sendNotification(GlobalData.application, content)
			LogUtil.print("JpushMessage", "Broadcast content: $content")
		} catch (e : Exception) {
			LogUtil.print("JpushMessage", "Broadcast failed: ${e.message}")
		}
	}

	// Handle type one messages
	private fun handleTypeOneMessage(jpushOrderBean : JpushBean) {
		when (jpushOrderBean.typeDesc) {
			"giveUp" -> giveUpOrder(jpushOrderBean)
			"revoke" -> revokeOrder(jpushOrderBean)
			"reDispatch" -> reDispatchOrder(jpushOrderBean)
			else -> LogUtil.print("JpushMessage", "Unknown typeDesc: ${jpushOrderBean.typeDesc}")
		}
	}

	// Handle new order messages
	private fun newOrderMsg(jpushOrderBean : JpushBean) {
		try {
			pushListener.get()?.newOrderMsg(jpushOrderBean)
		} catch (e : Exception) {
			LogUtil.print("JpushMessage", "Failed to handle new order message: ${e.message}")
		}
	}

	// Handle give up order messages
	private fun giveUpOrder(jpushOrderBean : JpushBean) {
		pushListener.get()?.giveUpOrder(jpushOrderBean)
	}

	// Handle revoke order messages
	private fun revokeOrder(jpushOrderBean : JpushBean) {
		pushListener.get()?.revokeOrder(jpushOrderBean)
	}

	// Handle re-dispatch order messages
	private fun reDispatchOrder(jpushOrderBean : JpushBean) {
		pushListener.get()?.reDispatchOrder(jpushOrderBean)
	}

	// Handle important tip messages
	private fun importantTip(jpushOrderBean : JpushBean) {
		pushListener.get()?.importantTip(jpushOrderBean)
	}

	// Disconnect from JPush and MQTT
	fun disconnect(context : Context) {
		try {
			JPushInterface.stopPush(context) // Stop JPush
			MyMqttClient.disconnect() // Disconnect MQTT
			LogUtil.print("ServiceManager", "Disconnected from JPush and MQTT successfully")
		} catch (e : Exception) {
			LogUtil.print("ServiceManager", "Error during disconnection: ${e.message}")
		}
	}


	private const val CHANNEL_ID = "ImportantMessagesChannel"
	private const val NOTIFICATION_ID = 1003

	// Initialize notification channel
	private fun createNotificationChannel(context : Context) {
		if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
			val channel = NotificationChannel(CHANNEL_ID,
				"订单通知",
				NotificationManager.IMPORTANCE_HIGH).apply {
				description = "用于接收重要消息通知"
				setSound(RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION),
					Notification.AUDIO_ATTRIBUTES_DEFAULT)
				enableVibration(true)
			}
			val notificationManager =
				context.getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager
			notificationManager.createNotificationChannel(channel)
		}
	}

	private fun sendSystemNotificationFromMessage(jpushOrderInfoBean : JpushBean) {
		when (jpushOrderInfoBean.pushType) {
			0 -> sendNotification(GlobalData.application,
				"您有新的 ${jpushOrderInfoBean.addressProperty ?: ""} ${jpushOrderInfoBean.serviceTypeName ?: ""}: ${jpushOrderInfoBean.taskCode ?: ""}")

			1 -> {
				when (jpushOrderInfoBean.typeDesc) {
					"giveUp" -> sendNotification(GlobalData.application,
						"订单:${jpushOrderInfoBean.taskCode ?: ""}已被放弃！")

					"revoke" -> sendNotification(GlobalData.application,
						"订单:${jpushOrderInfoBean.taskCode ?: ""}已被撤回！")

					"reDispatch" -> sendNotification(GlobalData.application,
						"订单:${jpushOrderInfoBean.taskCode ?: ""}被改派！")

					else -> {}
				}
			}

			3 -> sendNotification(GlobalData.application,
				"重要提醒：${jpushOrderInfoBean.tipContent ?: ""}")

			else -> {}
		}
	}

	// Send notification
	private fun sendNotification(context : Context, message : String) {
		createNotificationChannel(context)
		val notification =
			NotificationCompat.Builder(context, CHANNEL_ID).setContentTitle("重要通知")
				.setContentText(message).setSmallIcon(R.mipmap.ic_launcher) // 替换为你的应用图标
				.setPriority(NotificationCompat.PRIORITY_HIGH).setAutoCancel(true) // 点击后自动取消通知
				.setSound(RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION))
				.setVibrate(longArrayOf(0, 100, 200, 300)).build()

		val notificationManager =
			context.getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager
		notificationManager.notify(NOTIFICATION_ID, notification)
	}


}