From 90f568cf48fcc3131b45a2081dea40015eae5c5b Mon Sep 17 00:00:00 2001
From: panlei <2799247126@qq.com>
Date: 星期六, 16 十一月 2019 18:00:33 +0800
Subject: [PATCH] 把数据格式化以及装配放进so
---
algorithm/middleware/middleware.go | 44 ++++
insertdata/insertDataToEs.go | 10
algorithm/car/car.go | 134 +++++++++++++
algorithm/middleware/readyData.go | 192 +++++++++++++++++++
ruleserver/ruleToformula.go | 34 +++
main.go | 137 +------------
structure/algorithm.go | 2
ruleserver/readyDataForRule.go | 31 ---
structure/rule.go | 5
9 files changed, 420 insertions(+), 169 deletions(-)
diff --git a/algorithm/car/car.go b/algorithm/car/car.go
new file mode 100644
index 0000000..473c493
--- /dev/null
+++ b/algorithm/car/car.go
@@ -0,0 +1,134 @@
+package main
+
+import (
+"basic.com/pubsub/protomsg.git"
+"basic.com/valib/logger.git"
+"github.com/knetic/govaluate"
+"ruleprocess/structure"
+"strconv"
+)
+
+// 杞︾墝绠楁硶
+
+func Entrance(rule *protomsg.Rule, am *structure.AreaMap,lable *structure.Others,args *structure.SdkDatas,message *protomsg.SdkMessage) structure.LittleRuleResult {
+ if rule.PolygonId == am.AreaId { // 棣栧厛杩欐潯瑙勫垯寰楁槸杩欎釜绠楁硶鐨勮鍒欙紝鍏舵瑙勫垯鎵�瀵瑰簲鐨勫尯鍩焛d瑕佽窡鍖哄煙鏁版嵁鐨刬d瀵圭殑涓�
+ if rule.SdkArgAlias != "nCarCount" && rule.SdkArgAlias != "nCarLogoCount" {
+ logger.Info("杩囨护杞︾墝淇℃伅")
+ return filterRule(rule, am)
+ } else {
+ logger.Info("璁$畻杞︾墝杞﹁締鏁伴噺") // 鐩墠鍙兘妫�娴嬪嚭杞︾墝鏁伴噺
+ return transferParameters(rule, am)
+ }
+ } else {
+ return structure.LittleRuleResult{}
+ }
+}
+
+
+
+// 杩囨护瑙勫垯鍏堢瓫閫夊嚭绗﹀悎鏉′欢鐨勭洰鏍囨暟閲�
+func filterRule(rule *protomsg.Rule, am *structure.AreaMap) structure.LittleRuleResult {
+ // 澶勭悊鐨勯兘鏄痽olo鏁版嵁
+ carFlag := rule.SdkArgAlias == "license" || rule.SdkArgAlias == "nColor" || rule.SdkArgAlias == "nConfidence" ||
+ rule.SdkArgAlias == "nBright" || rule.SdkArgAlias == "nTime" || rule.SdkArgAlias == "nCarBright" || rule.SdkArgAlias == "nCarColor" ||
+ rule.SdkArgAlias == "nCarLogo" || rule.SdkArgAlias == "nCarType" || rule.SdkArgAlias == "nCarModel" || rule.SdkArgAlias == "nCarModelConfidence"
+
+ if rule.SdkArgAlias == "score" || rule.SdkArgAlias == "proportion" || rule.SdkArgAlias == "size" || carFlag{ // 鍒ゆ柇鐨勬槸鐩镐技鍊硷紝鍗犳瘮锛屽昂瀵哥瓑杩囨护鏉′欢锛屽鏋滃啀鏈夛紝杩樺彲浠ュ啀鍔�
+ logger.Debug("---------璧颁簡杞︾墝璇嗗埆杩囨护绠楁硶",rule.Id,rule.SdkArgAlias,rule.Operator,rule.SdkArgValue,am.AreaId)
+ var args []*structure.Arg
+ if rule.RuleWithPre == "&&" {
+ args = am.FilterData
+ } else {
+ args = am.Args
+ }
+ // 鍏堟竻绌鸿繃婊ゅ悗鐨勬暟鎹紝鍐嶅線閲屽鏈杩囨护鍚庣殑鏁版嵁
+ am.FilterData = am.FilterData[0:0]
+ //logger.Debug("鐪嬬湅args锛氾細锛氾細锛�", args)
+ for _, arg := range args {
+ var formula string
+ switch rule.SdkArgAlias {
+ case "score":
+ formula = strconv.FormatFloat(arg.Score, 'f', -1, 64) + " " + rule.Operator + " " + rule.SdkArgValue
+ logger.Info("褰撳墠鐩镐技搴﹀皬鍏紡锛�", formula)
+ case "proportion":
+ formula = strconv.FormatFloat(arg.Proportion, 'f', -1, 64) + " " + rule.Operator + " " + rule.SdkArgValue
+ logger.Info("鍗犳瘮鍏紡锛�", formula)
+ case "size":
+ formula = strconv.FormatFloat(arg.Size, 'f', -1, 64) + " " + rule.Operator + " " + rule.SdkArgValue
+ logger.Info("灏哄灏忓叕寮忥細", formula)
+ case "license":
+ formula = arg.Car.License + " " + rule.Operator + " " + rule.SdkArgValue
+ logger.Info("褰撳墠杞︾墝鍙风爜灏忓叕寮忥細", formula)
+ case "nColor":
+ formula = strconv.Itoa(int(arg.Car.NColor)) + " " + rule.Operator + " " + rule.SdkArgValue
+ logger.Info("杞︾墝棰滆壊灏忓叕寮忥細", formula)
+ case "nConfidence":
+ formula = strconv.Itoa(int(arg.Car.NConfidence)) + " " + rule.Operator + " " + rule.SdkArgValue
+ logger.Info("鏁寸墝鍙俊搴﹀皬鍏紡锛�", formula)
+ case "nBright":
+ formula = strconv.Itoa(int(arg.Car.NBright)) + " " + rule.Operator + " " + rule.SdkArgValue
+ logger.Info("杞︾墝浜害璇勪环灏忓叕寮忥細", formula)
+ case "nDirection":
+ formula = strconv.Itoa(int(arg.Car.NDirection)) + " " + rule.Operator + " " + rule.SdkArgValue
+ logger.Info("杞︾墝杩愬姩鏂瑰悜灏忓叕寮忥細", formula)
+ case "nTime":
+ formula = strconv.Itoa(int(arg.Car.NTime)) + " " + rule.Operator + " " + rule.SdkArgValue
+ logger.Info("璇嗗埆鑰楁椂灏忓叕寮忥細", formula)
+ case "nCarBright":
+ formula = strconv.Itoa(int(arg.Car.NCarBright)) + " " + rule.Operator + " " + rule.SdkArgValue
+ logger.Info("杞︾殑浜害灏忓叕寮忥細", formula)
+ case "nCarColor":
+ formula = strconv.Itoa(int(arg.Car.NCarColor)) + " " + rule.Operator + " " + rule.SdkArgValue
+ logger.Info("杞︾殑棰滆壊灏忓叕寮忥細", formula)
+ case "nCarLogo":
+ formula = strconv.Itoa(int(arg.Car.NCarLogo)) + " " + rule.Operator + " " + rule.SdkArgValue
+ logger.Info("杞︽爣绫诲瀷灏忓叕寮忥細", formula)
+ case "nCarType":
+ formula = strconv.Itoa(int(arg.Car.NCarType)) + " " + rule.Operator + " " + rule.SdkArgValue
+ logger.Info("杞﹁締绫诲瀷灏忓叕寮忥細", formula)
+ //case "nCarModel":
+ // formula = strconv.Itoa(int(arg.Car.ncm)) + " " + rule.Operator + " " + rule.SdkArgValue
+ // logger.Info("璇嗗埆鎴愬姛涓庡惁灏忓叕寮忥細", formula)
+ //case "nCarModelConfidence":
+ // formula = strconv.Itoa(int(arg.Car.NCarModelConfidence)) + " " + rule.Operator + " " + rule.SdkArgValue
+ // logger.Info("杞﹀瀷鍙俊搴﹀皬鍏紡锛�", formula)
+ }
+ expression, _ := govaluate.NewEvaluableExpression(formula) // 寰楀埌鏁板鍏紡
+ result, _ := expression.Evaluate(nil) // 寰楀埌鏁板鍏紡鐨勭粨鏋�
+ if result.(bool) {
+ am.FilterData = append(am.FilterData, arg) // 寰楀埌绗﹀悎鏉′欢鐨勮繃婊ゆ暟鎹�
+ }
+ }
+ am.TargetNum = len(am.FilterData) // 鎶婄鍚堟潯浠剁殑鐩爣鏁伴噺鏇存柊鍒皌argetNum瀛楁
+ if am.TargetNum > 0 {
+ return structure.LittleRuleResult{am.SdkName, rule.RuleWithPre + "" + "true", rule.Sort}
+ } else {
+ return structure.LittleRuleResult{am.SdkName, rule.RuleWithPre + "" + "false", rule.Sort}
+ }
+
+ } else if rule.SdkArgAlias == "" {
+ if am.TargetNum > 0 {
+ return structure.LittleRuleResult{am.SdkName, rule.RuleWithPre + "" + "true", rule.Sort}
+ } else {
+ return structure.LittleRuleResult{am.SdkName, rule.RuleWithPre + "" + "false", rule.Sort}
+ }
+ }
+ return structure.LittleRuleResult{}
+}
+
+
+// 缁欐暟鎹簱鐨勮鍒欒〃杈惧紡浠e弬 args: 涓�鏉″瓙瑙勫垯锛屽尯鍩熸暟鎹�
+func transferParameters(rule *protomsg.Rule, am *structure.AreaMap) structure.LittleRuleResult {
+ //logger.Info("褰撳墠灏忚鍒欐槸锛�---------", rule)
+ //logger.Info("寰楀嚭缁撴灉闃舵", "姣旇緝鐨勮鍒欐槸锛�", rule)
+ if rule.Operator == "" {
+ return structure.LittleRuleResult{am.SdkName, strconv.Itoa(am.TargetNum) + "" + rule.RuleWithPre, rule.Sort} // 濡傛灉鍚庨潰涓嶈窡鎿嶄綔绗﹀氨鐩存帴杩斿洖鏁伴噺 姣斿瑕佽窡涓嬩竴涓尯鍩熸瘮杈冩暟閲忕殑灏辩洿鎺ヨ繑鍥炴湰鍖哄煙鐨勬暟閲�
+ }
+ //args := am.targetNum targetNum 宸叉垚鎵�鏈夌洰鏍囩殑鎬绘暟閲忥紝杩欓噷鍙畻yolo鐨�
+ var num int = len(am.FilterData)
+ formula := strconv.Itoa(num) + " " + rule.Operator + " " + rule.SdkArgValue
+ expression, _ := govaluate.NewEvaluableExpression(formula) // 寰楀埌鏁板鍏紡
+ result, _ := expression.Evaluate(nil) // 寰楀埌鏁板鍏紡鐨勭粨鏋�
+ return structure.LittleRuleResult{am.SdkName, rule.RuleWithPre + " " + strconv.FormatBool(result.(bool)), rule.Sort}
+ // 鍔犱笂鍏充簬绠楁硶鐨勫垽鏂潯浠讹紝涓嶈兘鍙湁鍏充簬瑙勫垯鐨勶紝鏈夌殑绠楁硶鏈韩灏辨槸涓�涓鍒欙紝濡備釜浣撻潤姝紝闈犲彸琛�,鎵�浠ワ紝鎷垮埌褰撳墠瀛愯鍒欑殑sdkid鏉ュ垽鏂槸鍚︽槸閭d簺鐗规畩鐨勮鍒�
+}
\ No newline at end of file
diff --git a/algorithm/middleware/middleware.go b/algorithm/middleware/middleware.go
index 3c890c2..60ea600 100644
--- a/algorithm/middleware/middleware.go
+++ b/algorithm/middleware/middleware.go
@@ -20,7 +20,13 @@
polygonId := ""
// 鍏堣繃瀹屾潯浠惰鍒�
for j := 0; j < len(groupRule.Rules); j++ {
- if groupRule.Rules[j].SdkArgAlias == "score" || groupRule.Rules[j].SdkArgAlias == "proportion" || groupRule.Rules[j].SdkArgAlias == "size" || (groupRule.Rules[j].SdkId == "812b674b-2375-4589-919a-5c1c3278a972" && groupRule.Rules[j].SdkArgAlias != "time_rule"){
+
+ carFlag := groupRule.Rules[j].SdkArgAlias == "license" || groupRule.Rules[j].SdkArgAlias == "nColor" || groupRule.Rules[j].SdkArgAlias == "nConfidence" ||
+ groupRule.Rules[j].SdkArgAlias == "nBright" || groupRule.Rules[j].SdkArgAlias == "nTime" || groupRule.Rules[j].SdkArgAlias == "nCarBright" || groupRule.Rules[j].SdkArgAlias == "nCarColor" ||
+ groupRule.Rules[j].SdkArgAlias == "nCarLogo" || groupRule.Rules[j].SdkArgAlias == "nCarType" || groupRule.Rules[j].SdkArgAlias == "nCarModel" || groupRule.Rules[j].SdkArgAlias == "nCarModelConfidence"
+
+ if groupRule.Rules[j].SdkArgAlias == "score" || groupRule.Rules[j].SdkArgAlias == "proportion" || groupRule.Rules[j].SdkArgAlias == "size" ||
+ (groupRule.Rules[j].SdkId == "812b674b-2375-4589-919a-5c1c3278a972" && groupRule.Rules[j].SdkArgAlias != "time_rule") || carFlag{
for _, sdkData := range args.Sdkdata {
// 鏍规嵁瑙勫垯鐨剆dkId鏌ュ嚭鍏跺搴旂殑ipcId锛岀敤ipcId鍘绘壘璇ユ瘮瀵圭殑鏁版嵁
sdk, err := cache.GetSdkById(groupRule.Rules[j].SdkId)
@@ -126,6 +132,42 @@
}
}
}
+ // 杞﹁締
+ for j := 0; j < len(groupRule.Rules); j++ {
+ if groupRule.Rules[j].SdkId == "812b674b-2375-4589-919a-5c1c3278a978" && (groupRule.Rules[j].SdkArgAlias == "nCarCount" || groupRule.Rules[j].SdkArgAlias == "nCarLogoCount"){
+ for _, sdkData := range args.Sdkdata {
+ // 鏍规嵁瑙勫垯鐨剆dkId鏌ュ嚭鍏跺搴旂殑ipcId锛岀敤ipcId鍘绘壘璇ユ瘮瀵圭殑鏁版嵁
+ sdk, err := cache.GetSdkById(groupRule.Rules[j].SdkId)
+ if err != nil {
+ logger.Error("娌℃煡鍒皊dk鐨勪俊鎭�---", err)
+ }
+ ipcId := sdk.IpcId
+ sdkName := sdk.SdkName
+ //logger.Info("瑙勫垯鐨刬pcId涓巗dkData鐨処pcId:", ipcId, "===", sdkData.IpcId)
+ if ipcId == sdkData.IpcId {
+ logger.Info("褰撳墠璧扮殑瑙勫垯鏄�--锛�", groupRule.Rules[j],sdkName,groupRule.Rules[j].SdkArgAlias, "---","")
+ for _, areaMap := range sdkData.AreaMapList {
+ ruleResult := CallSo(sdk.Id, groupRule.Rules[j], areaMap,lable,args,message)
+ if ruleResult.Result != "" {
+ logger.Info("杞︾墝缁撴灉锛�", ruleResult.Result)
+ // 濡傛灉缁撴灉涓虹湡锛屾妸杩欐潯瑙勫垯涓殑鍖哄煙缃负鏈夋晥
+ if strings.Contains(ruleResult.Result, "true") {
+ areaMap.IsEffective = true
+ }
+ // 濡傛灉姝ょ粨鏋滀负鐪熶笖褰撳墠杩囩殑鏄痽olo绠楁硶锛屽簲璁颁笅姝よ鍒欐墍瀵瑰簲鐨剆dkName,鍙﹀锛岃繕瑕佸幓閲� (鍚庡姞锛氭妸姝ゆ潯瑙︾鐨勫尯鍩焛d涔熻褰曚笅鏉�)
+ if strings.Contains(ruleResult.Result, "true") && ipcId == "02D54B61-0F16-C604-8567-FC4BE493C523" && !strings.Contains(sdkNames, sdkName) {
+ sdkNames = sdkName + " "
+ }
+ if strings.Contains(ruleResult.Result, "true") && ipcId == "02D54B61-0F16-C604-8567-FC4BE493C523" && !strings.Contains(polygonId, groupRule.Rules[j].PolygonId) {
+ polygonId += groupRule.Rules[j].PolygonId + ","
+ }
+ resultSplice = append(resultSplice, &ruleResult)
+ }
+ }
+ }
+ }
+ }
+ }
// 鍐嶈繃鍏朵粬鏁版嵁 杩欐鐩存帴寰楀埌缁撴灉锛堢湡鎴栧亣锛� 杩囩洰鏍囨暟閲�
for j := 0; j < len(groupRule.Rules); j++ {
if groupRule.Rules[j].SdkArgAlias == "objCount" {
diff --git a/algorithm/middleware/readyData.go b/algorithm/middleware/readyData.go
new file mode 100644
index 0000000..84ec173
--- /dev/null
+++ b/algorithm/middleware/readyData.go
@@ -0,0 +1,192 @@
+package main
+
+import (
+ "basic.com/pubsub/protomsg.git"
+ "basic.com/valib/logger.git"
+ "github.com/golang/protobuf/proto"
+ uuid "github.com/satori/go.uuid"
+ "ruleprocess/ruleserver"
+ "ruleprocess/structure"
+ "ruleprocess/util"
+ "strconv"
+ "time"
+)
+func ReadData(args *structure.SdkDatas,cameraPolygons []protomsg.CameraPolygon) {
+ for _, arg := range args.Sdkdata {
+ SdkDataFormat(args.CameraId, arg, cameraPolygons)
+ }
+}
+
+// 璁$畻鍖哄煙鍐呯殑鐩爣鏁伴噺浠ュ強灏嗙浉浼煎害銆佸崰姣斻�佸昂瀵哥瓑鎵撳寘
+func CountAreaObjs(a *structure.AreaMap,arg *structure.SdkData) {
+
+ a.TargetNum = 0
+ threshold := 80.0 // 鐩镐技搴�
+ intersectionper := 20.0 // 鍗犳瘮
+ size := 0.0 // 灏哄
+
+ areaPoints := ruleserver.Json2points(a.AreaJson)
+ logger.Info("鐪嬬湅鍥剧墖鐨剋idth鍜宧eight:",arg.ImageWidth,arg.ImageHeight)
+ widthScale := float64(arg.ImageWidth) / 960
+ heigthScale := float64(arg.ImageHeight) / 540
+ for _, obj := range arg.Photo {
+ //logger.Info("------------------鐪嬬湅sdkData:", arg.SdkName, "鐨凱hoto鏁版嵁----------------", obj, "----椤轰究鐪嬬湅鍗犳瘮-----锛�", PgsInterPercent(areaPoints, obj.Rects, widthScale, heigthScale))
+ if obj.Score >= threshold && float64(obj.Rects.Width*obj.Rects.Height) >= size && ruleserver.PgsInterPercent(areaPoints, obj.Rects, widthScale, heigthScale) >= intersectionper {
+ // 杩欐瑕佸榻愯〃杈惧紡閲屾墍闇�瑕佺殑鎵�鏈夊弬鏁�
+ a.TargetNum++
+ uuid := uuid.NewV4().String()
+ arg1 := structure.Arg{obj.Id,uuid,obj.Score, ruleserver.PgsInterPercent(areaPoints, obj.Rects, widthScale, heigthScale), float64(obj.Rects.Width * obj.Rects.Height), a.AreaJson,obj.IsYolo, obj.Rects, obj.Car,obj.Feature, obj.ThftRes, []*structure.BaseInfo{},"",structure.ResultMsg{}}
+ //logger.Println("鏀捐繘鍘荤殑arg锛�-------", arg1)
+ a.Args = append(a.Args, &arg1)
+ a.FilterData = append(a.FilterData, &arg1)
+ }
+ }
+ logger.Info("鍖哄煙鏄細",areaPoints,"鍖哄煙鍐呯洰鏍囨暟閲忎负锛�",a.TargetNum,"---",len(a.FilterData))
+ a.Time = time.Unix(time.Now().Unix(), 0).String()[11:16]
+ //logger.Println("--------------------鐪嬬湅鍖哄煙鏁版嵁锛�",*a)
+}
+
+// 鎶妔dk浠庢暟鎹抚涓婃彁鍙栫殑鎸夌収鍖哄煙鍒嗙被褰掔疆
+func SdkDataFormat(cameraId string, arg *structure.SdkData, cameraPolygons []protomsg.CameraPolygon) {
+ logger.Info("==================================鏈瑂dkData涓В鍑烘潵鐨勭洰鏍囨暟鎹�=======================================")
+ for _, photo := range arg.Photo {
+ logger.Info("--------瑙f瀽鍑烘潵鐨勬暟鎹�---", cameraId, arg.IpcId, photo.Rects, photo.Score)
+ }
+ for _, polygon := range cameraPolygons {
+ //logger.Println("++++++鍦ㄨ繖鍎跨湅涓�涓嬪尯鍩熷晩:", polygon.Polygon)
+ areaMap := structure.AreaMap{CameraId: cameraId, AreaId: polygon.Id, AreaJson: polygon.Polygon, TriggerLine: polygon.TriggerLine, DirectionLine: polygon.DirectionLine}
+ // 涓烘瘡涓憚鍍忔満鍖哄煙濉厖鏁版嵁
+ CountAreaObjs(&areaMap,arg)
+ arg.AreaMapList = append(arg.AreaMapList, &areaMap)
+ }
+}
+
+
+
+// 灏嗗閮ㄤ紶杩涙潵鐨剅ect锛坱op,bottom,left,right锛夎浆鍖栦负鑷繁鍐呴儴鐨剅ect(left top width height)
+func rectFormat(rcobj *protomsg.Rect) structure.Rect {
+ //logger.Info("++++++++++++++++++++++++++++++鏀跺埌鐨剏olo鐨勫尯鍩熷潗鏍囷細",rcobj)
+ rect := structure.Rect{}
+ rect.X = float64(rcobj.Left)
+ rect.Y = float64(rcobj.Top)
+ rect.Width = float64(rcobj.Right - rcobj.Left)
+ rect.Height = float64(rcobj.Bottom - rcobj.Top)
+ return rect
+}
+
+
+
+
+// 灏嗗閮ㄤ紶杩涙潵鐨剆dk鏁版嵁鍖呰В鎴� SdkDatas
+func ParamFormat(msg []byte, args *structure.SdkDatas) protomsg.SdkMessage {
+ defer func() {
+ if err := recover(); err != nil {
+ logger.Info("瑙e寘杩囩▼鐨勫紓甯告崟鑾�", err.(string))
+ }
+
+ }()
+ // 鍙嶅簭鍒楀寲鏁版嵁寰楀埌sdk鍏ュ弬
+ m := protomsg.SdkMessage{}
+ err := proto.Unmarshal(msg, &m)
+ if err != nil {
+ panic("瑙f瀽msg鏃跺嚭鐜伴敊璇�")
+ }
+
+ // 鍏堣繘琛屼竴涓嬭拷韪�
+ ruleserver.FaceIsSame(&m)
+ args.CameraId = m.Cid
+ args.TaskId = m.Tasklab.Taskid
+ // 鎶婂浘鐗囩殑浜岃繘鍒惰В鍘嬬缉杩涜鐢绘鍦ㄥ帇缂╁洖鍘�
+ bdata, err := util.UnCompress(m.Data)
+ if err != nil {
+ panic("瑙e帇缂╁浘鐗囨椂鍑虹幇閿欒")
+ }
+ i := protomsg.Image{}
+ err = proto.Unmarshal(bdata, &i)
+ logger.Info("鎺ュ埌鏁版嵁锛屾憚鍍忔満涓猴細", m.Cid, "鍥剧墖鐨刬d涓猴細", i.Id)
+ //logger.Info("----------------鐪嬬湅鏈夊嚑涓畻娉曪細",len(m.Tasklab.Sdkinfos))
+ for _, sdkinfo := range m.Tasklab.Sdkinfos { // yolo绠楁硶
+ if sdkinfo.Sdktype == "Yolo" {
+ arg := structure.SdkData{}
+ arg.TaskId = m.Tasklab.Taskid
+ arg.IpcId = sdkinfo.Ipcid
+ arg.IsYolo = true
+ arg.ImageWidth = int(i.Width)
+ arg.ImageHeight = int(i.Height)
+ logger.Info("-----杩借釜涔嬪悗sdkinfo.Sdkdata鐨勯暱搴︿负锛�----", len(sdkinfo.Sdkdata))
+ if len(sdkinfo.Sdkdata) > 1 {
+ // 澶т簬1鎵嶆湁鏁版嵁
+ yoloParam := protomsg.ParamYoloObj{}
+ err = proto.Unmarshal(sdkinfo.Sdkdata, &yoloParam)
+ if err != nil {
+ logger.Info("瑙f瀽YOLO sdk鏁版嵁鏃跺嚭鐜伴敊璇�", err)
+ continue
+ }
+ var yoloNum int = 0
+ for _, info := range yoloParam.Infos {
+ if info.Typ == 0 {
+ //logger.Debug("-------------yolo鐨勫潗鏍囨湁鍑犱釜",info.RcObj)
+ photoMap := structure.PhotoMap{Rects: rectFormat(info.RcObj), Score: float64(info.Prob) * 100, IsYolo: true,Id:strconv.Itoa(int(info.ObjID))}
+ arg.Photo = append(arg.Photo, photoMap)
+ yoloNum++
+ }
+ }
+ logger.Info("--------------杩借釜涔嬪悗yolo鐨勪釜鏁帮細", yoloNum)
+ args.Sdkdata = append(args.Sdkdata, &arg)
+ } else {
+ continue
+ }
+
+ }
+ if sdkinfo.Sdktype == "FaceDetect" { // 浜鸿劯妫�娴�
+ arg := structure.SdkData{}
+ arg.TaskId = m.Tasklab.Taskid
+ arg.IpcId = sdkinfo.Ipcid
+ arg.IsYolo = false
+ arg.ImageWidth = int(i.Width)
+ arg.ImageHeight = int(i.Height)
+ if len(sdkinfo.Sdkdata) > 1 {
+ faceParam := protomsg.ParamFacePos{}
+ err = proto.Unmarshal(sdkinfo.Sdkdata, &faceParam)
+ if err != nil {
+ logger.Info("瑙f瀽FACE sdk鏁版嵁鏃跺嚭鐜伴敊璇�", err)
+ continue
+ }
+ logger.Info("--------------杩借釜涔嬪悗浜鸿劯鐨勪釜鏁帮細", len(faceParam.Faces))
+ for _, info := range faceParam.Faces {
+ //logger.Info("_______________________________________________绗竴娆$湅鐩镐技鍊硷細",info.Pos.FAngle.Confidence*100)
+ photoMap := structure.PhotoMap{Id: strconv.Itoa(int(info.Pos.FaceID)) , Rects: rectFormat(info.Pos.RcFace), Score: float64(info.Pos.FAngle.Confidence * 100), IsYolo: false, ThftRes: *(info.Result), Feature: info.Feats}
+ arg.Photo = append(arg.Photo, photoMap)
+ }
+ args.Sdkdata = append(args.Sdkdata, &arg)
+ } else {
+ continue
+ }
+ }
+ if sdkinfo.Sdktype == "Plate" { // 杞︾墝璇嗗埆
+ arg := structure.SdkData{}
+ arg.TaskId = m.Tasklab.Taskid
+ arg.IpcId = sdkinfo.Ipcid
+ arg.IsYolo = false
+ arg.ImageWidth = int(i.Width)
+ arg.ImageHeight = int(i.Height)
+ if len(sdkinfo.Sdkdata) > 1 {
+ plateIDResult := protomsg.PlateIDResult {}
+ err = proto.Unmarshal(sdkinfo.Sdkdata, &plateIDResult )
+ if err != nil {
+ logger.Info("瑙f瀽杞︾墝鏁版嵁鏃跺嚭鐜伴敊璇�", err)
+ continue
+ }
+ for _, info := range plateIDResult.Result {
+ logger.Info("鎺ユ敹杞︾墝鏁版嵁锛�",info)
+ photoMap := structure.PhotoMap{Score: float64(info.NConfidence),Rects: rectFormat(info.RcLocation), IsYolo: false, Car:info}
+ arg.Photo = append(arg.Photo, photoMap)
+ }
+ args.Sdkdata = append(args.Sdkdata, &arg)
+ } else {
+ continue
+ }
+ }
+ }
+ return m
+}
diff --git a/insertdata/insertDataToEs.go b/insertdata/insertDataToEs.go
index 41f90c8..30443c8 100644
--- a/insertdata/insertDataToEs.go
+++ b/insertdata/insertDataToEs.go
@@ -233,7 +233,7 @@
ageDescription := getDescription(face.ThftRes.Age)
logger.Info(ageDescription)
var target = new(Target)
- target.TargetId = strconv.FormatUint(face.Id, 10)
+ target.TargetId = face.Id
target.TargetScore = face.Score
target.TargetLocation = Points{TopLeft: Point{face.Location.X, face.Location.Y}, BottomRight: Point{face.Location.X + face.Location.Width, face.Location.Y + face.Location.Height}}
//logger.Info("浜鸿劯鐨刬d:",strconv.FormatUint(face.Id, 10))
@@ -397,14 +397,14 @@
// 鍘婚噸娣诲姞
var flag = true
for _, selectTarget := range targetInfos {
- if strconv.FormatUint(target.Id, 10) == selectTarget.TargetId {
+ if target.Id == selectTarget.TargetId {
flag = false
break
}
}
if flag {
var target1 = new(Target)
- target1.TargetId = strconv.FormatUint(target.Id, 10)
+ target1.TargetId = target.Id
target1.TargetScore = target.Score
target1.TargetLocation = Points{TopLeft: Point{target.Location.X, target.Location.Y}, BottomRight: Point{target.Location.X + target.Location.Width, target.Location.Y + target.Location.Height}}
targetInfos = append(targetInfos, *target1)
@@ -812,14 +812,14 @@
// 鍘婚噸娣诲姞
var flag = true
for _, selectTarget := range targetInfos {
- if strconv.FormatUint(target.Id, 10) == selectTarget.TargetId {
+ if target.Id == selectTarget.TargetId {
flag = false
break
}
}
if flag {
var target1 = new(Target)
- target1.TargetId = strconv.FormatUint(target.Id, 10)
+ target1.TargetId = target.Id
target1.TargetScore = target.Score
target1.TargetLocation = Points{TopLeft: Point{target.Location.X, target.Location.Y}, BottomRight: Point{target.Location.X + target.Location.Width, target.Location.Y + target.Location.Height}}
targetInfos = append(targetInfos, *target1)
diff --git a/main.go b/main.go
index 3528a6a..8fb18fc 100644
--- a/main.go
+++ b/main.go
@@ -6,21 +6,19 @@
"basic.com/valib/deliver.git"
"net/http"
_ "net/http/pprof"
+ "plugin"
"ruleprocess/insertdata"
"ruleprocess/labelFilter"
"ruleprocess/structure"
- "ruleprocess/util"
"time"
"basic.com/valib/logger.git"
"flag"
"fmt"
- "github.com/golang/protobuf/proto"
-
+ "github.com/spf13/viper"
"ruleprocess/cache"
"ruleprocess/ruleserver"
"sync"
- "github.com/spf13/viper"
)
var dbIp = flag.String("dbIp", "127.0.0.1", "dbserver ip")
@@ -93,7 +91,7 @@
arg := structure.SdkDatas{}
//paramFormat(msg, &arg)
start := time.Now()
- m := paramFormat(msg, &arg)
+ m := CallParamFormat(msg, &arg)
// 杩涜瑙勫垯澶勭悊鍒ゆ柇(鎵撲笂瑙勫垯鐨勬爣绛�)
ruleserver.Judge(&arg, &m) // 鎶妔dkMessage浼犺繘鍘伙紝鏂逛究缂撳瓨鏁版嵁鏃舵嫾鍑轰竴涓猺esultMag
// 鎶奱rg閲岀殑鎵撶殑鏍囩鎷垮嚭鏉ョ粰m鍐嶅皝瑁呬竴灞�
@@ -113,128 +111,15 @@
}
}
-
-// 灏嗗閮ㄤ紶杩涙潵鐨剅ect锛坱op,bottom,left,right锛夎浆鍖栦负鑷繁鍐呴儴鐨剅ect(left top width height)
-func rectFormat(rcobj *protomsg.Rect) structure.Rect {
- //logger.Info("++++++++++++++++++++++++++++++鏀跺埌鐨剏olo鐨勫尯鍩熷潗鏍囷細",rcobj)
- rect := structure.Rect{}
- rect.X = float64(rcobj.Left)
- rect.Y = float64(rcobj.Top)
- rect.Width = float64(rcobj.Right - rcobj.Left)
- rect.Height = float64(rcobj.Bottom - rcobj.Top)
- return rect
-}
-
-// 灏嗗閮ㄤ紶杩涙潵鐨剆dk鏁版嵁鍖呰В鎴� SdkDatas
-func paramFormat(msg []byte, args *structure.SdkDatas) protomsg.SdkMessage {
- defer func() {
- if err := recover(); err != nil {
- logger.Info("瑙e寘杩囩▼鐨勫紓甯告崟鑾�", err.(string))
- }
-
- }()
- // 鍙嶅簭鍒楀寲鏁版嵁寰楀埌sdk鍏ュ弬
- m := protomsg.SdkMessage{}
- err := proto.Unmarshal(msg, &m)
+func CallParamFormat(msg []byte, args *structure.SdkDatas) protomsg.SdkMessage{
+ p,err := plugin.Open("./algorithm/middleware.so")
if err != nil {
- panic("瑙f瀽msg鏃跺嚭鐜伴敊璇�")
+ panic(err)
}
-
- // 鍏堣繘琛屼竴涓嬭拷韪�
- ruleserver.FaceIsSame(&m)
- args.CameraId = m.Cid
- args.TaskId = m.Tasklab.Taskid
- // 鎶婂浘鐗囩殑浜岃繘鍒惰В鍘嬬缉杩涜鐢绘鍦ㄥ帇缂╁洖鍘�
- bdata, err := util.UnCompress(m.Data)
- if err != nil {
- panic("瑙e帇缂╁浘鐗囨椂鍑虹幇閿欒")
+ f,err1 := p.Lookup("ParamFormat")
+ if err1 != nil {
+ panic("娌℃湁鎵惧埌涓棿浠跺叆鍙e嚱鏁�")
}
- i := protomsg.Image{}
- err = proto.Unmarshal(bdata, &i)
- logger.Info("鎺ュ埌鏁版嵁锛屾憚鍍忔満涓猴細", m.Cid, "鍥剧墖鐨刬d涓猴細", i.Id)
- //logger.Info("----------------鐪嬬湅鏈夊嚑涓畻娉曪細",len(m.Tasklab.Sdkinfos))
- for _, sdkinfo := range m.Tasklab.Sdkinfos { // yolo绠楁硶
- if sdkinfo.Sdktype == "Yolo" {
- arg := structure.SdkData{}
- arg.TaskId = m.Tasklab.Taskid
- arg.IpcId = sdkinfo.Ipcid
- arg.IsYolo = true
- arg.ImageWidth = int(i.Width)
- arg.ImageHeight = int(i.Height)
- logger.Info("-----杩借釜涔嬪悗sdkinfo.Sdkdata鐨勯暱搴︿负锛�----", len(sdkinfo.Sdkdata))
- if len(sdkinfo.Sdkdata) > 1 {
- // 澶т簬1鎵嶆湁鏁版嵁
- yoloParam := protomsg.ParamYoloObj{}
- err = proto.Unmarshal(sdkinfo.Sdkdata, &yoloParam)
- if err != nil {
- logger.Info("瑙f瀽YOLO sdk鏁版嵁鏃跺嚭鐜伴敊璇�", err)
- continue
- }
- var yoloNum int = 0
- for _, info := range yoloParam.Infos {
- if info.Typ == 0 {
- //logger.Debug("-------------yolo鐨勫潗鏍囨湁鍑犱釜",info.RcObj)
- photoMap := structure.PhotoMap{Rects: rectFormat(info.RcObj), Score: float64(info.Prob) * 100, IsYolo: true,Id:info.ObjID}
- arg.Photo = append(arg.Photo, photoMap)
- yoloNum++
- }
- }
- logger.Info("--------------杩借釜涔嬪悗yolo鐨勪釜鏁帮細", yoloNum)
- args.Sdkdata = append(args.Sdkdata, &arg)
- } else {
- continue
- }
-
- }
- if sdkinfo.Sdktype == "FaceDetect" { // 浜鸿劯妫�娴�
- arg := structure.SdkData{}
- arg.TaskId = m.Tasklab.Taskid
- arg.IpcId = sdkinfo.Ipcid
- arg.IsYolo = false
- arg.ImageWidth = int(i.Width)
- arg.ImageHeight = int(i.Height)
- if len(sdkinfo.Sdkdata) > 1 {
- faceParam := protomsg.ParamFacePos{}
- err = proto.Unmarshal(sdkinfo.Sdkdata, &faceParam)
- if err != nil {
- logger.Info("瑙f瀽FACE sdk鏁版嵁鏃跺嚭鐜伴敊璇�", err)
- continue
- }
- logger.Info("--------------杩借釜涔嬪悗浜鸿劯鐨勪釜鏁帮細", len(faceParam.Faces))
- for _, info := range faceParam.Faces {
- //logger.Info("_______________________________________________绗竴娆$湅鐩镐技鍊硷細",info.Pos.FAngle.Confidence*100)
- photoMap := structure.PhotoMap{Id: info.Pos.FaceID, Rects: rectFormat(info.Pos.RcFace), Score: float64(info.Pos.FAngle.Confidence * 100), IsYolo: false, ThftRes: *(info.Result), Feature: info.Feats}
- arg.Photo = append(arg.Photo, photoMap)
- }
- args.Sdkdata = append(args.Sdkdata, &arg)
- } else {
- continue
- }
- }
- if sdkinfo.Sdktype == "Plate" { // 杞︾墝璇嗗埆
- arg := structure.SdkData{}
- arg.TaskId = m.Tasklab.Taskid
- arg.IpcId = sdkinfo.Ipcid
- arg.IsYolo = false
- arg.ImageWidth = int(i.Width)
- arg.ImageHeight = int(i.Height)
- if len(sdkinfo.Sdkdata) > 1 {
- plateIDResult := protomsg.PlateIDResult {}
- err = proto.Unmarshal(sdkinfo.Sdkdata, &plateIDResult )
- if err != nil {
- logger.Info("瑙f瀽杞︾墝鏁版嵁鏃跺嚭鐜伴敊璇�", err)
- continue
- }
- for _, info := range plateIDResult.Result {
- logger.Info("鎺ユ敹杞︾墝鏁版嵁锛�",info)
- photoMap := structure.PhotoMap{Rects: rectFormat(info.RcLocation), IsYolo: false, Car:info}
- arg.Photo = append(arg.Photo, photoMap)
- }
- args.Sdkdata = append(args.Sdkdata, &arg)
- } else {
- continue
- }
- }
- }
- return m
+ mess := f.(func(msg []byte, args *structure.SdkDatas)(protomsg.SdkMessage))(msg,args)
+ return mess
}
diff --git a/ruleserver/readyDataForRule.go b/ruleserver/readyDataForRule.go
index 3b1388f..5fb9ac4 100644
--- a/ruleserver/readyDataForRule.go
+++ b/ruleserver/readyDataForRule.go
@@ -93,35 +93,6 @@
//logger.Info("鍒濇淇濈暀涓や綅鎴恠tr::::",value2)
return value2
}
-// 鍙栧嚭鏌愪釜鏃堕棿瑙勫垯鐨勭鍑犲ぉ鐨勮鍒欐闆嗗悎
-func GetTimeById(id string, index int) []structure.TimeRange {
- _, cameraTimeRule := cache.GetTimeRuleById(id)
- var timeRangeList []structure.Day
- err := json.Unmarshal([]byte(cameraTimeRule.TimeRule), &timeRangeList)
- if err != nil {
- logger.Error("鍙栨椂闂磋鍒欐椂鍙嶅簭鍒楀寲閿欒锛�")
- }
- for _, timerange := range timeRangeList {
- if timerange.Day == index {
- //logger.Println("鍙栧埌鐨勬椂闂磋鍒欙細", timerange.TimeRange)
- return timerange.TimeRange
- }
- }
- return nil
-}
-
-// 鏍规嵁浼犲叆鐨勫瓧绗︿覆寰楀埌鍏跺湪涓�鍛ㄥ唴鐨勭储寮� 鍛ㄤ竴鍒板懆鏃ュ垎鍒搴�1鍒�7
-func getIndexOfWeek(weekday string) int {
- var weekdays = [7]string{"Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"}
- for k, value := range weekdays {
- if value == weekday {
- return k + 1 // 鍥犱负鏁版嵁搴撲腑瀛樼殑鏄�1-7浠h〃鐨勫懆涓�鍒板懆鏃�
- }
- }
- return 0
-}
-
-
// 灏嗗瓧绗︿覆鏍煎紡鐨勫潗鏍囧簭鍒楀寲涓篜oint鏍煎紡
func Json2points(areaPoints string) []structure.Point {
@@ -275,7 +246,7 @@
// 杩欐瑕佸榻愯〃杈惧紡閲屾墍闇�瑕佺殑鎵�鏈夊弬鏁�
a.TargetNum++
uuid := uuid.NewV4().String()
- arg1 := structure.Arg{obj.Id,uuid,obj.Score, PgsInterPercent(areaPoints, obj.Rects, widthScale, heigthScale), float64(obj.Rects.Width * obj.Rects.Height), a.AreaJson,obj.IsYolo, obj.Rects, obj.Feature, obj.ThftRes, []*structure.BaseInfo{},"",structure.ResultMsg{}}
+ arg1 := structure.Arg{obj.Id,uuid,obj.Score, PgsInterPercent(areaPoints, obj.Rects, widthScale, heigthScale), float64(obj.Rects.Width * obj.Rects.Height), a.AreaJson,obj.IsYolo, obj.Rects, obj.Car,obj.Feature, obj.ThftRes, []*structure.BaseInfo{},"",structure.ResultMsg{}}
//logger.Println("鏀捐繘鍘荤殑arg锛�-------", arg1)
a.Args = append(a.Args, &arg1)
a.FilterData = append(a.FilterData, &arg1)
diff --git a/ruleserver/ruleToformula.go b/ruleserver/ruleToformula.go
index 8c63f1c..3c34c77 100644
--- a/ruleserver/ruleToformula.go
+++ b/ruleserver/ruleToformula.go
@@ -27,9 +27,7 @@
cameraPolygons := GetPolygons(args.CameraId)
// 鎶婃墍鏈夌殑sdk鎻愬彇鐨勬暟鎹兘鎸夋墍灞炴憚鍍忔満鐨勫尯鍩熷綊缃�
logger.Debug("褰撳墠鎽勫儚鏈篿d涓猴細",message.Cid,"褰撳墠鎽勫儚鏈烘墽琛岀殑浠诲姟鏄細",message.Tasklab.Taskname,"--浠诲姟id涓猴細",message.Tasklab.Taskid)
- for _, arg := range args.Sdkdata {
- SdkDataFormat(args.CameraId, arg, cameraPolygons)
- }
+ CallReadyData(args,cameraPolygons)
// 璺戞湰鎽勫儚鏈虹殑鎵�鏈夎鍒欑粍 涓�缁勪竴缁勮窇
taskGroup := GetRuleGroup(args.CameraId, args.TaskId) // 鏈憚鍍忔満鏈换鍔′笅鎵�鏈夎鍒欑粍
//logger.Println("鐪嬩笅鎽勫儚鏈轰笅鐨勪换鍔$粍锛�",taskRuleList)
@@ -88,6 +86,18 @@
}
a,b,c := f.(func(args *structure.SdkDatas,rule protomsg.GroupRule,label *structure.Others,message *protomsg.SdkMessage)(bool,string, string))(args,rule,lable,message)
return a,b,c
+}
+
+func CallReadyData(args *structure.SdkDatas,cameraPolygons []protomsg.CameraPolygon) {
+ p,err := plugin.Open("./algorithm/middleware.so")
+ if err != nil {
+ panic(err)
+ }
+ f,err1 := p.Lookup("ReadyData")
+ if err1 != nil {
+ panic("娌℃湁鎵惧埌涓棿浠跺叆鍙e嚱鏁�")
+ }
+ f.(func(args *structure.SdkDatas,cameraPolygons []protomsg.CameraPolygon)())(args,cameraPolygons)
}
func RunRule(args *structure.SdkDatas, groupRule *protomsg.GroupRule, taskId string, message *protomsg.SdkMessage, label structure.Others) (bool,[]int) {
@@ -169,10 +179,21 @@
// 澶勭悊鐩爣瀹氭椂鏁版嵁
targets := []*structure.Arg{}
for _, sdkData := range args.Sdkdata {
- if sdkData.IpcId == "02D54B61-0F16-C604-8567-FC4BE493C523" && sdkNames != "" { // 鎶妝olo鏁版嵁鐨勫悇涓洰鏍囩殑鍧愭爣杈撳嚭鏂逛究鍚庨潰鐢绘
+ if sdkData.IpcId == "02D54B61-0F16-C604-8567-FC4BE493C523" && sdkNames != "" { // 杈撳嚭鐩爣鏁版嵁
for _, areaMap := range sdkData.AreaMapList {
if areaMap.IsEffective {
targets = append(targets, putTargetsToResult(areaMap)...)
+ }
+ }
+ }
+ }
+ // 杞﹁締鐩爣缁熻
+ cars := []*structure.Arg{}
+ for _, sdkData := range args.Sdkdata {
+ if sdkData.IpcId == "91d923ef-6200-4549-ab1b-8e773e85d729" && sdkNames != "" { // 鎶妝olo鏁版嵁鐨勫悇涓洰鏍囩殑鍧愭爣杈撳嚭鏂逛究鍚庨潰鐢绘
+ for _, areaMap := range sdkData.AreaMapList {
+ if areaMap.IsEffective {
+ cars = append(cars, putYolosToResult(areaMap)...)
}
}
}
@@ -199,6 +220,11 @@
logger.Info("-------------------鐩爣鎸佺画缁撴灉鏍囩", len(args.RuleResult["target"].([]structure.Result)))
//labelTypes = append(labelTypes,2)
}
+ if len(cars) > 0 {
+ args.RuleResult["car"] = append(args.RuleResult["car"].([]structure.Result), structure.Result{taskId, sdkNames, groupRule.GroupId, groupRule.DefenceState, groupRule.AlarmLevel, groupRule.GroupText, cars, polygonId, islink,label})
+ logger.Info("-------------------鐩爣鎸佺画缁撴灉鏍囩", len(args.RuleResult["target"].([]structure.Result)))
+ //labelTypes = append(labelTypes,2)
+ }
// 缁欐寔缁椂闂寸殑绗竴寮犺祴浜堢紦瀛樻暟鎹紙閬嶅巻澶嶅埗锛�
if cacheId != "" { // 鏈夎繖甯ф暟鎹殑缂撳瓨
tempMap := make(map[string]interface{})
diff --git a/structure/algorithm.go b/structure/algorithm.go
index e40b2c2..b8c6e5c 100644
--- a/structure/algorithm.go
+++ b/structure/algorithm.go
@@ -7,7 +7,7 @@
Targets []*Obj
}
type Obj struct {
- Id uint64
+ Id string
Location Rect
N int // 璁℃暟鍣ㄥ綋鍓嶅��
InitN int // 璁℃暟鍣ㄥ垵濮嬪��
diff --git a/structure/rule.go b/structure/rule.go
index 0ac2187..d038743 100644
--- a/structure/rule.go
+++ b/structure/rule.go
@@ -6,7 +6,7 @@
// 姣忎釜鐩爣鐨勫弬鏁帮細鐩镐技搴︼紝鍗犳瘮锛屽昂瀵�
type Arg struct {
- Id uint64
+ Id string
Uuid string
Score float64 // 鍖哄煙鍐呯殑鐩爣鐨勭浉浼煎害
Proportion float64 // 鍖哄煙鍐呯殑鐩爣鐨勫崰姣�
@@ -14,6 +14,7 @@
AreaJson string // 鎵�灞炲尯鍩�
IsYolo bool // 鏄惁鏄痽olo鏁版嵁
Location Rect // 璁颁笅姣忎釜鐩爣鐨勪綅缃弬鏁帮紝鏈�鍚庣粰缁撴灉瑁呴厤鐩爣鏁版嵁鐨勬椂鍊欑敤鐨勫埌
+ Car *protomsg.PlateID // 杞﹁締鍙傛暟
Feature []byte
ThftRes protomsg.ThftResult
Liker []*BaseInfo
@@ -42,7 +43,7 @@
// sdk杈撳嚭鐨勫浘鐗囦笂鍗曚釜鐩爣鐨勬暟鎹�
type PhotoMap struct {
- Id uint64
+ Id string
Rects Rect // 鐭╁舰鍖哄煙鍙傛暟
Score float64 // 鐩镐技搴﹀緱鍒嗭紙鏈夊澶х▼搴﹀儚涓�涓洰鏍囥�備汉鑴革紝浜轰綋鎴栬溅绛夌瓑锛�
IsYolo bool // 鏄惁鏄痽olo鏁版嵁
--
Gitblit v1.8.0