#coding: utf-8
import json
import re
import threading
import time
import traceback

import cv2
import requests

from lib.service.StreamH264Flv import StreamH264Flv


class FlvPressureTest():

    def __init__(self):
        self.mobileStart = 100000000000                                                            # 开始手机号
        self.channel = 1                                                                           # 频道号
        self.terNum = 2                                                                            # 要压力测试的线程数
        self.flvPath = "../../flv/aaa3.flv"                                                        # 要推流的视频路劲
        self.host = "10.100.12.3"
        self.port = 1078
        self.sendDur = 0.005                                                                       # socket消息发送间隔
        self.isShowFrame = 0                                                                       # 拉流是否展示画面  0：不展示  1：展示
        self.getGetPlayUrl = "http://10.100.11.110:9999/video/streamInfo"                          # 获取推流播放地址的url
        # self.getGetPlayUrl = "http://fb-test.vandyo.com/video/streamInfo"                          # 获取推流播放地址的url

        self.threadInfo = {}                                                                       # 存放线程集
        self.threadInfo["threadObj"] = {}
        self.threadInfo["sucessT"] = {}
        self.threadInfo["failT"] = {}

        self.threadInfoPull = {}                                                                   # 存放线程集（拉流线程）
        self.threadInfoPull["threadObj"] = {}
        self.threadInfoPull["sucessT"] = {}
        self.threadInfoPull["failT"] = {}
        self.isOpenPullStream = 1                                                                  # 是否开启视频拉流  0：不  1：是

    def setTerNum(self, data):
        self.terNum = data
    def setMobileStart(self, data="10000000000"):
        self.mobileStart = data
    def setChannel(self, data):
        self.channel = data
    def setFlvPath(self, data):
        self.flvPath = data
    def setHost(self, data):
        self.host = data
    def setPort(self, data):
        self.port = data
    def setIsOpenPullStream(self, data):
        self.isOpenPullStream = data
    def setSendDur(self,data):
        self.sendDur = data
    def setIsShowFrame(self,data):
        self.isShowFrame = data

    def getThreadInfo(self):
        return self.threadInfo
    def getThreadInfoPull(self):
        return self.threadInfoPull

    def testServicePush(self, cloudMirror,threadName):
        try:
            cloudMirror.readFlvAndSend()
        except:
            traceback.print_exc()
            self.threadInfo["threadObj"].pop(threadName)
            return
        self.threadInfo["threadObj"].pop(threadName)

    def testServicePull(self, mobile,threadName):
        pullUrl = self.getPlayUrl(mobile,self.channel)
        # pullUrl = self.replaceHost(pullUrl, "video-test.vandyo.com:")
        cap = cv2.VideoCapture(pullUrl)
        try:
            while (cap.isOpened()):
                ret, frame = cap.read()
                if ret == False:
                    break
                if self.isShowFrame == 1:
                    cv2.imshow("video", frame)
                if cv2.waitKey(1) & 0xFF == ord('q'):
                    break
            print("拉流结束")
            cap.release()
            cv2.destroyAllWindows()
        except:
            traceback.print_exc()
            self.threadInfoPull["threadObj"].pop(threadName)
            return
        self.threadInfoPull["threadObj"].pop(threadName)

    ################################################
    #      启动推流线程
    ################################################
    def runPush(self, mobile, threadId):
        cloudMirror = StreamH264Flv()
        cloudMirror.setHost(self.host)
        cloudMirror.setPort(self.port)
        cloudMirror.connectServer()
        cloudMirror.setVideoPath(self.flvPath)
        cloudMirror.setMobile(mobile)
        cloudMirror.setChannel(self.channel)
        cloudMirror.setSendDur(self.sendDur)

        conThread = threading.Thread(target=self.testServicePush, args=(cloudMirror,threadId))
        self.threadInfo["threadObj"][threadId] = conThread
        conThread.start()
        print(threadId + "启动了：" + mobile + "-" + str(self.channel))

    ################################################
    #      启动拉流线程
    ################################################
    def runPull(self, mobile, threadId):
        time.sleep(1)
        pullThread = threading.Thread(target=self.testServicePull, args=(mobile,threadId))
        self.threadInfoPull["threadObj"][threadId] = pullThread
        pullThread.start()
        print(threadId + "启动了：" + mobile + "-" + str(self.channel))

    ################################################
    #      启动压力测试服务
    ################################################
    def start(self):
        for i in range(0, self.terNum):
            mobile = self.mobileStart + i
            mobile = "0" + str(mobile)
            threadId = "threadId__" + str(i)
            self.runPush(mobile, threadId)
            time.sleep(0.01)

        if self.isOpenPullStream == 1:
            for j in range(0, self.terNum):
                mobile = self.mobileStart + j
                mobile = "0" + str(mobile)
                threadPullId = "threadPullId__" + str(j)
                self.runPull(mobile, threadPullId)
                time.sleep(0.01)

    ####################################################
    #      获取视频播放地址
    ####################################################
    def getPlayUrl(self,mobile,channel):
        res = requests.post(self.getGetPlayUrl, data=json.dumps({'devId': mobile,'chan': str(channel)})).text
        res = json.loads(res)
        return res["data"]["url"]

    ####################################################
    #      替换url的host
    ####################################################
    def replaceHost(self,url,replaceWord):
        data = url
        strinfo = re.compile('(\d+.\d+.\d+.\d+.:)')
        result = strinfo.sub(replaceWord, data)
        return result

if __name__ == "__main__":
    test = FlvPressureTest()
    test.setHost("10.100.11.125")
    # test.setHost("video-test.vandyo.com")
    test.setPort(1078)
    test.setMobileStart(10000000000)
    test.setChannel(1)
    test.setTerNum(1)
    test.setIsOpenPullStream(1)                            # 设置是否开启拉流
    test.setIsShowFrame(0)                                 # 拉流是否显示预览画面
    test.setSendDur(0.007)
    test.setFlvPath("../../flv/aaa3.flv")
    test.start()