559 lines
14 KiB
Go
559 lines
14 KiB
Go
package ys7
|
||
|
||
import (
|
||
"context"
|
||
"encoding/json"
|
||
"fmt"
|
||
"io"
|
||
"net/http"
|
||
"os"
|
||
"time"
|
||
|
||
"github.com/gogf/gf/v2/encoding/gjson"
|
||
"github.com/gogf/gf/v2/frame/g"
|
||
"github.com/gogf/gf/v2/os/gctx"
|
||
"github.com/tiger1103/gfast/v3/internal/app/system/dao"
|
||
)
|
||
|
||
var accessToken = "at.ddhhz6ea49jorccubhg3elqs19nvmxta-1754nu5ce8-017egq8-fmymwvvhv"
|
||
|
||
const (
|
||
Ok = "200"
|
||
Online = 1
|
||
)
|
||
|
||
// 改变 accessToken
|
||
func SetAccessToken(token string) {
|
||
accessToken = token
|
||
}
|
||
|
||
// 传入 serial 返回 Devicemap 中的设备信息
|
||
func GetDevice(serial string) (Ys7Device, error) {
|
||
device, ok := deviceMap[serial]
|
||
if ok {
|
||
return device, nil
|
||
}
|
||
return Ys7Device{}, fmt.Errorf("设备不存在")
|
||
}
|
||
|
||
var deviceMap = make(map[string]Ys7Device)
|
||
|
||
/*当前包的入口方法*/
|
||
func InitYs7() {
|
||
/*获取一次token*/
|
||
getAccessToken()
|
||
/*获取一次设备列表*/
|
||
getDeviceList(0, 50) // 可以提前获取数据库中的记录进行缓存,比对当前设备是否在数据库中已经存在,不存在则自动入库
|
||
}
|
||
|
||
func GetAccessToken() string {
|
||
return accessToken
|
||
}
|
||
|
||
/*获取设备表*/
|
||
func GetDeviceMap() map[string]Ys7Device {
|
||
return deviceMap
|
||
}
|
||
|
||
type TokenRes struct {
|
||
Public
|
||
Data struct {
|
||
AccessToken string `json:"accessToken"`
|
||
ExpireTime int64 `json:"expireTime"`
|
||
} `json:"data"`
|
||
}
|
||
|
||
func getAccessToken() {
|
||
// ctx := gctx.New()
|
||
// appKey := g.Cfg().MustGet(ctx, "ys7.appKey").String()
|
||
// appSecret := g.Cfg().MustGet(ctx, "ys7.appSecret").String()
|
||
|
||
appKey := "3acf9f1a43dc4209841e0893003db0a2"
|
||
appSecret := "4bbf3e9394f55d3af6e3af27b2d3db36"
|
||
|
||
url := "https://open.ys7.com/api/lapp/token/get"
|
||
dt := struct {
|
||
AppKey string `json:"appKey"`
|
||
AppSecret string `json:"appSecret"`
|
||
}{AppKey: appKey, AppSecret: appSecret}
|
||
post, err := Post(url, dt)
|
||
if err != nil {
|
||
} else {
|
||
res := TokenRes{}
|
||
err = json.Unmarshal(post, &res)
|
||
if err != nil {
|
||
} else {
|
||
accessToken = res.Data.AccessToken
|
||
}
|
||
}
|
||
}
|
||
|
||
type DeviceListRes struct {
|
||
Public
|
||
Page struct {
|
||
Total int `json:"total"`
|
||
Page int `json:"page"`
|
||
Size int `json:"size"`
|
||
} `json:"page"`
|
||
Data []Ys7Device `json:"data"`
|
||
}
|
||
|
||
func delayRequest(page, pageSize int) {
|
||
time.Sleep(time.Second * 5)
|
||
getDeviceList(page, pageSize)
|
||
}
|
||
|
||
func getDeviceList(page, pageSize int) {
|
||
url := "https://open.ys7.com/api/lapp/device/list"
|
||
dt := struct {
|
||
AccessToken string `json:"accessToken"`
|
||
PageStart int `json:"pageStart"`
|
||
PageSize int `json:"pageSize"`
|
||
}{AccessToken: accessToken, PageSize: pageSize, PageStart: page}
|
||
post, err := Post(url, dt)
|
||
if err != nil {
|
||
delayRequest(page, pageSize)
|
||
} else {
|
||
res := DeviceListRes{}
|
||
err = json.Unmarshal(post, &res)
|
||
if err != nil {
|
||
delayRequest(page, pageSize)
|
||
} else {
|
||
if res.Code == Ok {
|
||
for _, datum := range res.Data {
|
||
deviceMap[datum.DeviceSerial] = datum
|
||
//marshal, err := json.Marshal(datum)
|
||
//if err != nil {
|
||
// return
|
||
//}
|
||
//fmt.Println(string(marshal))
|
||
//if datum.Online() {
|
||
// capRes, err := datum.Capture()
|
||
// if err != nil {
|
||
// fmt.Println("抓图识别")
|
||
// } else {
|
||
// SavePicture(capRes.Data.PicUrl, "static/"+gmd5.MustEncryptString(capRes.Data.PicUrl)+".jpg")
|
||
// }
|
||
//}
|
||
}
|
||
if (page+1)*pageSize < res.Page.Total {
|
||
getDeviceList(page+1, pageSize)
|
||
}
|
||
} else {
|
||
delayRequest(page, pageSize)
|
||
}
|
||
}
|
||
}
|
||
}
|
||
|
||
type Ys7Device struct {
|
||
DeviceSerial string `json:"deviceSerial"`
|
||
DeviceName string `json:"deviceName"`
|
||
DeviceType string `json:"deviceType"`
|
||
Status int `json:"status"`
|
||
Defence int `json:"defence"`
|
||
DeviceVersion string `json:"deviceVersion"`
|
||
}
|
||
type Public struct {
|
||
Code string `json:"code"`
|
||
Msg string `json:"msg"`
|
||
}
|
||
|
||
func (receiver *Ys7Device) Online() bool {
|
||
if receiver.Status == Online {
|
||
return true
|
||
} else {
|
||
return false
|
||
}
|
||
}
|
||
|
||
func Post(url string, data interface{}) (res []byte, err error) {
|
||
response, err := g.Client().Header(map[string]string{"Content-Type": "application/x-www-form-urlencoded"}).Post(gctx.New(), url, data)
|
||
if err != nil {
|
||
return nil, err
|
||
}
|
||
return response.ReadAll(), nil
|
||
}
|
||
|
||
/*开始云台控制*/
|
||
func (receiver *Ys7Device) PTZStart(direction int) (res *Public, err error) {
|
||
url := "https://open.ys7.com/api/lapp/device/ptz/start"
|
||
dt := struct {
|
||
ChannelNo int `json:"channelNo"`
|
||
Direction int `json:"direction"`
|
||
Speed int `json:"speed"`
|
||
DeviceSerial string `json:"deviceSerial"`
|
||
AccessToken string `json:"accessToken"`
|
||
}{
|
||
AccessToken: accessToken, DeviceSerial: receiver.DeviceSerial, ChannelNo: 1, Speed: 1, Direction: direction,
|
||
}
|
||
post, err := Post(url, dt)
|
||
if err != nil {
|
||
return nil, err
|
||
} else {
|
||
res = &Public{}
|
||
err = json.Unmarshal(post, &res)
|
||
if err != nil {
|
||
return nil, err
|
||
}
|
||
return
|
||
}
|
||
}
|
||
|
||
/*停止云台控制*/
|
||
func (receiver *Ys7Device) PTZEnd(direction int) (res *Public, err error) {
|
||
url := "https://open.ys7.com/api/lapp/device/ptz/stop"
|
||
dt := struct {
|
||
ChannelNo int `json:"channelNo"`
|
||
Direction int `json:"direction"`
|
||
DeviceSerial string `json:"deviceSerial"`
|
||
AccessToken string `json:"accessToken"`
|
||
}{
|
||
AccessToken: accessToken, DeviceSerial: receiver.DeviceSerial, ChannelNo: 1, Direction: direction,
|
||
}
|
||
post, err := Post(url, dt)
|
||
if err != nil {
|
||
return nil, err
|
||
} else {
|
||
res = &Public{}
|
||
err = json.Unmarshal(post, &res)
|
||
if err != nil {
|
||
return nil, err
|
||
}
|
||
return
|
||
}
|
||
}
|
||
|
||
type PresetAddRes struct {
|
||
Public
|
||
Data struct {
|
||
Index int `json:"index"` // 预置点序号,C6设备是1-12,该参数需要开发者自行保存
|
||
} `json:"data"`
|
||
}
|
||
|
||
/*添加预制点*/
|
||
func (receiver *Ys7Device) AddPreset() (res *PresetAddRes, err error) {
|
||
url := "https://open.ys7.com/api/lapp/device/preset/add"
|
||
dt := struct {
|
||
ChannelNo int `json:"channelNo"`
|
||
DeviceSerial string `json:"deviceSerial"`
|
||
AccessToken string `json:"accessToken"`
|
||
}{
|
||
AccessToken: accessToken, DeviceSerial: receiver.DeviceSerial, ChannelNo: 1,
|
||
}
|
||
post, err := Post(url, dt)
|
||
if err != nil {
|
||
return nil, err
|
||
} else {
|
||
res = &PresetAddRes{}
|
||
err = json.Unmarshal(post, &res)
|
||
if err != nil {
|
||
return nil, err
|
||
}
|
||
return
|
||
}
|
||
}
|
||
|
||
/*调用预制点*/
|
||
func (receiver *Ys7Device) MovePreset(index int) (res *Public, err error) {
|
||
url := "https://open.ys7.com/api/lapp/device/preset/move"
|
||
dt := struct {
|
||
ChannelNo int `json:"channelNo"`
|
||
DeviceSerial string `json:"deviceSerial"`
|
||
AccessToken string `json:"accessToken"`
|
||
Index int `json:"index"`
|
||
}{ChannelNo: 1, DeviceSerial: receiver.DeviceSerial, AccessToken: accessToken, Index: index}
|
||
post, err := Post(url, dt)
|
||
if err != nil {
|
||
return nil, err
|
||
} else {
|
||
res = &Public{}
|
||
err = json.Unmarshal(post, &res)
|
||
if err != nil {
|
||
return nil, err
|
||
}
|
||
return
|
||
}
|
||
}
|
||
|
||
/*清除预制点*/
|
||
func (receiver *Ys7Device) ClearPreset(index int) (res *Public, err error) {
|
||
url := "https://open.ys7.com/api/lapp/device/preset/clear"
|
||
dt := struct {
|
||
ChannelNo int `json:"channelNo"`
|
||
DeviceSerial string `json:"deviceSerial"`
|
||
AccessToken string `json:"accessToken"`
|
||
Index int `json:"index"`
|
||
}{ChannelNo: 1, DeviceSerial: receiver.DeviceSerial, AccessToken: accessToken, Index: index}
|
||
post, err := Post(url, dt)
|
||
if err != nil {
|
||
return nil, err
|
||
} else {
|
||
res = &Public{}
|
||
err = json.Unmarshal(post, &res)
|
||
if err != nil {
|
||
return nil, err
|
||
}
|
||
return
|
||
}
|
||
}
|
||
|
||
// 开启设备视频加密
|
||
func (r *Ys7Device) OpenEncrypt() error {
|
||
url := "https://open.ys7.com/api/lapp/device/encrypt/on"
|
||
dt := struct {
|
||
AccessToken string `json:"accessToken"`
|
||
DeviceSerial string `json:"deviceSerial"`
|
||
}{
|
||
AccessToken: accessToken,
|
||
DeviceSerial: r.DeviceSerial,
|
||
}
|
||
|
||
post, err := Post(url, dt)
|
||
if err != nil {
|
||
return err
|
||
}
|
||
|
||
if gjson.New(string(post)).Get("code").Int() != 200 {
|
||
return fmt.Errorf("%s", gjson.New(string(post)).Get("msg").String())
|
||
}
|
||
|
||
// 更新数据库
|
||
_, err = dao.Ys7Devices.Ctx(context.Background()).
|
||
Where(dao.Ys7Devices.Columns().DeviceSerial, r.DeviceSerial).
|
||
Update(g.Map{
|
||
"VideoEncrypted": 1,
|
||
})
|
||
if err != nil {
|
||
return err
|
||
}
|
||
|
||
return nil
|
||
}
|
||
|
||
// 关闭设备视频加密
|
||
func (r *Ys7Device) CloseEncrypt() error {
|
||
url := "https://open.ys7.com/api/lapp/device/encrypt/off"
|
||
dt := struct {
|
||
AccessToken string `json:"accessToken"`
|
||
DeviceSerial string `json:"deviceSerial"`
|
||
}{
|
||
AccessToken: accessToken,
|
||
DeviceSerial: r.DeviceSerial,
|
||
}
|
||
|
||
post, err := Post(url, dt)
|
||
if err != nil {
|
||
return err
|
||
}
|
||
|
||
if gjson.New(string(post)).Get("code").Int() != 200 {
|
||
return fmt.Errorf("%s", gjson.New(string(post)).Get("msg").String())
|
||
}
|
||
|
||
_, err = dao.Ys7Devices.Ctx(context.Background()).
|
||
Where(dao.Ys7Devices.Columns().DeviceSerial, r.DeviceSerial).
|
||
Update(g.Map{
|
||
"VideoEncrypted": 0,
|
||
})
|
||
if err != nil {
|
||
return err
|
||
}
|
||
|
||
return nil
|
||
}
|
||
|
||
// GetLiveAddress 获取播放地址
|
||
func (r *Ys7Device) GetLiveAddress() (string, error) {
|
||
url := "https://open.ys7.com/api/lapp/v2/live/address/get"
|
||
dt := struct {
|
||
AccessToken string `json:"accessToken"`
|
||
DeviceSerial string `json:"deviceSerial"`
|
||
ChannelNo int `json:"channelNo"`
|
||
}{
|
||
AccessToken: accessToken,
|
||
DeviceSerial: r.DeviceSerial,
|
||
ChannelNo: 1,
|
||
}
|
||
|
||
post, err := Post(url, dt)
|
||
if err != nil {
|
||
return "", err
|
||
}
|
||
|
||
Body := string(post)
|
||
println(Body)
|
||
if gjson.New(Body).Get("code").Int() != 200 {
|
||
return "", fmt.Errorf("获取播放地址失败: %s", gjson.New(Body).Get("msg").String())
|
||
}
|
||
|
||
return gjson.New(Body).Get("data.url").String(), nil
|
||
}
|
||
|
||
/*抓图结果返回*/
|
||
type CapRes struct {
|
||
Public
|
||
Data struct {
|
||
PicUrl string `json:"picUrl"`
|
||
} `json:"data"`
|
||
}
|
||
|
||
/*抓拍图片*/
|
||
func (receiver *Ys7Device) Capture() (cap *CapRes, err error) {
|
||
url := "https://open.ys7.com/api/lapp/device/capture"
|
||
dt := struct {
|
||
DeviceSerial string `json:"deviceSerial"`
|
||
ChannelNo int `json:"channelNo"`
|
||
AccessToken string `json:"accessToken"`
|
||
}{DeviceSerial: receiver.DeviceSerial, ChannelNo: 1, AccessToken: accessToken}
|
||
res, err := Post(url, dt)
|
||
if err != nil {
|
||
return nil, err
|
||
}
|
||
cap = &CapRes{}
|
||
err = json.Unmarshal(res, &cap)
|
||
if err != nil {
|
||
return nil, err
|
||
}
|
||
// cap.Data.PicUrl = string(TransHtmlJson([]byte(cap.Data.PicUrl)))
|
||
return cap, nil
|
||
}
|
||
|
||
// download file会将url下载到本地文件,它会在下载时写入,而不是将整个文件加载到内存中。
|
||
|
||
func SavePicture(url, dst string) (err error) {
|
||
// Get the data
|
||
resp, err := http.Get(url)
|
||
if err != nil {
|
||
return err
|
||
}
|
||
defer resp.Body.Close()
|
||
// Create the file
|
||
out, err := os.Create(dst)
|
||
if err != nil {
|
||
return err
|
||
}
|
||
defer out.Close()
|
||
|
||
// Write the body to file
|
||
_, err = io.Copy(out, resp.Body)
|
||
return err
|
||
}
|
||
|
||
//var appKey = ""
|
||
//var secret = ""
|
||
//var token = ""
|
||
//
|
||
//// InitYs7 安全帽 absolutePath绝对路径
|
||
//func InitYs7(absolutePath string) (flag bool, num int, err error) {
|
||
// getConfig()
|
||
// GetAccesstoken()
|
||
// imageData, err := os.ReadFile(absolutePath)
|
||
// if err != nil {
|
||
// err = errors.New("读取图片文件失败")
|
||
// return
|
||
// }
|
||
//
|
||
// // 将图片数据转换为Base64字符串
|
||
// base64String := base64.StdEncoding.EncodeToString(imageData)
|
||
// flag, num, err = HelmetCheck(base64String, absolutePath)
|
||
// return
|
||
//}
|
||
//
|
||
//func getConfig() {
|
||
// appKey = g.Cfg().MustGet(gctx.New(), "ys7.key").String()
|
||
// secret = g.Cfg().MustGet(gctx.New(), "ys7.secret").String()
|
||
//}
|
||
//
|
||
//func GetAccesstoken() {
|
||
// key := "ys7"
|
||
// //从缓存捞取key
|
||
// ctx := gctx.New()
|
||
// get := commonService.Cache().Get(ctx, key)
|
||
// if get != nil && get.String() != "" {
|
||
// token = get.String()
|
||
// } else {
|
||
// getConfig()
|
||
// url := "https://open.ys7.com/api/lapp/token/get"
|
||
// dt := struct {
|
||
// AppKey string `json:"appKey"`
|
||
// AppSecret string `json:"appSecret"`
|
||
// }{appKey, secret}
|
||
// err, s := post(url, dt)
|
||
// if err != nil {
|
||
// return
|
||
// }
|
||
// tp := TP{}
|
||
// err = json.Unmarshal(s, &tp)
|
||
// if err != nil {
|
||
// return
|
||
// }
|
||
// if tp.Code == OK {
|
||
// token = tp.Data.AccessToken
|
||
// //将token存储到redis中,tiken默认时间为秒,实际计算为7天,(这里少100秒,防止token过期还存在redis中)
|
||
// commonService.Cache().Set(ctx, key, tp.Data.AccessToken, time.Duration(tp.Data.ExpireTime-100)*time.Second)
|
||
// token = tp.Data.AccessToken
|
||
// }
|
||
// }
|
||
//
|
||
//}
|
||
//
|
||
//func post(uri string, data interface{}) (error, []byte) {
|
||
// response, err := g.Client().ContentType("application/x-www-form-urlencoded").Post(gctx.New(), uri, data)
|
||
// if err != nil {
|
||
// return err, nil
|
||
// }
|
||
// return nil, response.ReadAll()
|
||
//}
|
||
//
|
||
//// HelmetCheck 图片中标记安全帽
|
||
//func HelmetCheck(image string, absolutePath string) (flag bool, num int, err error) {
|
||
// flag = false
|
||
// num = 0
|
||
// url := "https://open.ys7.com/api/lapp/intelligence/target/analysis"
|
||
// dt := struct {
|
||
// AccessToken string `json:"accessToken"`
|
||
// DataType int `json:"dataType"`
|
||
// Image string `json:"image"`
|
||
// ServiceType string `json:"serviceType"`
|
||
// }{token, 1, image, "helmet"}
|
||
// err, s := post(url, dt)
|
||
// if err != nil {
|
||
// return
|
||
// }
|
||
// tp := HelMet{}
|
||
// err = json.Unmarshal(s, &tp)
|
||
// if err != nil {
|
||
// return
|
||
// }
|
||
// if tp.Code == OK && len(tp.Data) > 0 {
|
||
// for _, data := range tp.Data {
|
||
// height, _ := strconv.ParseFloat(data.Height, 64)
|
||
// width, _ := strconv.ParseFloat(data.Width, 64)
|
||
// if len(tp.Data) <= 0 {
|
||
// continue
|
||
// }
|
||
// for _, dataTwo := range data.TargetList {
|
||
// HeadRect := dataTwo.HeadRect
|
||
// helmetType := dataTwo.HelmetType
|
||
// if helmetType == 2 || helmetType == 0 {
|
||
// flag = true
|
||
// num = num + 1
|
||
// vmodel_h_f, _ := strconv.ParseFloat(HeadRect.VmodelHF, 64)
|
||
// vmodel_w_f, _ := strconv.ParseFloat(HeadRect.VmodelWF, 64)
|
||
// vmodel_x_f, _ := strconv.ParseFloat(HeadRect.VmodelXF, 64)
|
||
// vmodel_y_f, _ := strconv.ParseFloat(HeadRect.VmodelYF, 64)
|
||
//
|
||
// vmodel_h_f = vmodel_h_f * height
|
||
// vmodel_w_f = vmodel_w_f * width
|
||
// vmodel_x_f = vmodel_x_f * width
|
||
// vmodel_y_f = vmodel_y_f * height
|
||
// coryCommon.Test_draw_rect_text(absolutePath,
|
||
// vmodel_x_f, vmodel_y_f, vmodel_w_f, vmodel_h_f)
|
||
// }
|
||
// }
|
||
// }
|
||
// }
|
||
// return
|
||
//}
|