@ -1,45 +1,47 @@ | |||
package main | |||
import ( | |||
"github.com/gofiber/fiber/v2" | |||
"time" | |||
"github.com/gofiber/fiber/v2" | |||
"log" | |||
"time" | |||
) | |||
type StatusResult struct { | |||
Code string `json:"code"` | |||
Message string `json:"msg"` | |||
Timestamp int64 `json:"timestamp"` | |||
Code string `json:"code"` | |||
Message string `json:"msg"` | |||
Timestamp int64 `json:"timestamp"` | |||
} | |||
type StatusResultEx struct { | |||
StatusResult | |||
Scene string `json:"scene"` | |||
SequenceId int `json:"sequenceId"` | |||
StatusResult | |||
Scene string `json:"scene"` | |||
SequenceId int64 `json:"sequenceId"` | |||
} | |||
func failureResponse(ctx *fiber.Ctx, code string, msg string, stat int) error { | |||
ctx.Response().SetStatusCode(stat) | |||
var ret = make(map[string]interface{}) | |||
ret["status"] = StatusResult{Code: code, Message: msg, Timestamp: time.Now().Unix()} | |||
return ctx.JSON(ret) | |||
log.Println("failureResponse:> ", ctx.Request().URI(), msg) | |||
ctx.Response().SetStatusCode(stat) | |||
var ret = make(map[string]interface{}) | |||
ret["status"] = StatusResult{Code: code, Message: msg, Timestamp: time.Now().Unix()} | |||
return ctx.JSON(ret) | |||
} | |||
func successResponse(ctx *fiber.Ctx, msg string) error { | |||
var ret = make(map[string]interface{}) | |||
ret["status"] = StatusResult{Code: "0", Message: msg, Timestamp: time.Now().Unix()} | |||
return ctx.JSON(ret) | |||
var ret = make(map[string]interface{}) | |||
ret["status"] = StatusResult{Code: "0", Message: msg, Timestamp: time.Now().Unix()} | |||
return ctx.JSON(ret) | |||
} | |||
func successResponseEx(ctx *fiber.Ctx, msg string, scene string, seq int) error { | |||
var ret = make(map[string]interface{}) | |||
ret["status"] = StatusResultEx{ | |||
StatusResult: StatusResult{ | |||
Code: "0", | |||
Message: msg, | |||
Timestamp: time.Now().Unix(), | |||
}, | |||
SequenceId: seq, | |||
Scene: scene, | |||
} | |||
return ctx.JSON(ret) | |||
func successResponseEx(ctx *fiber.Ctx, msg string, scene string, seq int64) error { | |||
var ret = make(map[string]interface{}) | |||
ret["status"] = StatusResultEx{ | |||
StatusResult: StatusResult{ | |||
Code: "0", | |||
Message: msg, | |||
Timestamp: time.Now().Unix(), | |||
}, | |||
SequenceId: seq, | |||
Scene: scene, | |||
} | |||
return ctx.JSON(ret) | |||
} |
@ -1,28 +1,133 @@ | |||
package main | |||
import ( | |||
"github.com/gofiber/fiber/v2" | |||
"errors" | |||
"github.com/gofiber/fiber/v2" | |||
"log" | |||
"time" | |||
) | |||
type TestCommand struct { | |||
Command string `json:"cmd"` | |||
SequenceId int `json:"sequenceId"` | |||
Command string `json:"cmd"` | |||
SequenceId int64 `json:"sequenceId"` | |||
} | |||
var currentTest *TestCommand | |||
var testChannel chan *TestCommand | |||
var testStopChannel chan bool | |||
func setTestCmd(c *fiber.Ctx) error { | |||
var testCmd TestCommand | |||
if err := c.BodyParser(&testCmd); nil != err { | |||
return failureResponse(c, "-1", err.Error(), 400) | |||
} else if nil == currentScene { | |||
return failureResponse(c, "1", "not in a working scene", 400) | |||
} else { | |||
currentTest = &testCmd | |||
return successResponse(c, "Updated successfully.") | |||
} | |||
var testCmd TestCommand | |||
if err := c.BodyParser(&testCmd); nil != err { | |||
return failureResponse(c, "-1", err.Error(), 400) | |||
} else if nil == currentScene { | |||
return failureResponse(c, "1", "not in a working scene", 400) | |||
} else { | |||
currentTest = &testCmd | |||
switch testCmd.Command { | |||
case "START": | |||
log.Println("START ...") | |||
if nil != currentTest { | |||
return failureResponse(c, "2", "A test already started", 403) | |||
} | |||
if e := recogTaskProc(&testCmd); nil != e { | |||
return failureResponse(c, "3", e.Error(), 409) | |||
} | |||
case "STOP": | |||
log.Println("STOP ...") | |||
case "CANCEL": | |||
log.Println("CANCEL ...") | |||
default: | |||
log.Println("UNKNOWN ...") | |||
} | |||
return successResponse(c, "Updated successfully.") | |||
} | |||
} | |||
func pullUpTask(seq int64) error { | |||
var tk = time.NewTicker(time.Second * 3) | |||
defer func() { | |||
tk.Stop() | |||
}() | |||
for { | |||
select { | |||
case <-testStopChannel: | |||
return nil | |||
case <-tk.C: | |||
log.Println("===") | |||
} | |||
} | |||
} | |||
func standJumpTask(seq int64) error { | |||
var tk = time.NewTicker(time.Second * 3) | |||
defer func() { | |||
tk.Stop() | |||
}() | |||
for { | |||
select { | |||
case <-testStopChannel: | |||
return nil | |||
case <-tk.C: | |||
log.Println("===") | |||
} | |||
} | |||
} | |||
func sitUpsTask(seq int64) error { | |||
var tk = time.NewTicker(time.Second * 3) | |||
defer func() { | |||
tk.Stop() | |||
}() | |||
for { | |||
select { | |||
case <-testStopChannel: | |||
return nil | |||
case <-tk.C: | |||
log.Println("===") | |||
} | |||
} | |||
} | |||
func raceTask(seq int64) error { | |||
var tk = time.NewTicker(time.Second * 3) | |||
defer func() { | |||
tk.Stop() | |||
}() | |||
for { | |||
select { | |||
case <-testStopChannel: | |||
return nil | |||
case <-tk.C: | |||
log.Println("===") | |||
} | |||
} | |||
} | |||
func recogTaskProc(cmd *TestCommand) error { | |||
testStopChannel = make(chan bool) | |||
if nil == currentScene { | |||
return errors.New("invalid scene state") | |||
} | |||
if nil == currentScene.proc { | |||
return errors.New("invalid scene mode processor") | |||
} | |||
currentTest = cmd | |||
go func() { | |||
defer func() { | |||
close(testStopChannel) | |||
currentTest = nil | |||
}() | |||
if e := currentScene.proc(cmd.SequenceId); nil != e { | |||
log.Println(">>>>", e) | |||
} | |||
}() | |||
return nil | |||
} | |||
func init() { | |||
currentTest = nil | |||
currentTest = nil | |||
testChannel = nil | |||
testStopChannel = nil | |||
} |
@ -1,71 +1,119 @@ | |||
package main | |||
import ( | |||
"errors" | |||
"github.com/gofiber/fiber/v2" | |||
"net/url" | |||
"errors" | |||
"github.com/gofiber/fiber/v2" | |||
"log" | |||
"net/url" | |||
"time" | |||
) | |||
var currentScene *SceneCommand | |||
type SceneCommand struct { | |||
Scene string `json:"scene"` | |||
PushUrl string `json:"pushUrl"` | |||
CameraUrls []string `json:"cameraURls"` | |||
Scene string `json:"scene"` | |||
PushUrl string `json:"pushUrl"` | |||
CameraUrls []string `json:"cameraURls"` | |||
proc func(int64) error | |||
} | |||
var currentScene *SceneCommand | |||
var sceneStopChannel chan bool | |||
func validateSceneCmd(cmd SceneCommand) error { | |||
switch cmd.Scene { | |||
case "pullUp", "standJump", "sitUps": | |||
if len(cmd.CameraUrls) < 1 { | |||
return errors.New("cameraUrls can not less than 1") | |||
} | |||
case "race": | |||
if len(cmd.CameraUrls) < 2 { | |||
return errors.New("cameraUrls can not less than 2") | |||
} | |||
default: | |||
return errors.New("unknown scene type:" + cmd.Scene) | |||
} | |||
if u, e := url.Parse(cmd.PushUrl); nil != e { | |||
return errors.New("invalid pushUrl:" + e.Error()) | |||
} else if u.Scheme != "http" && u.Scheme != "https" { | |||
return errors.New("can not support pushUrl with " + u.Scheme) | |||
} | |||
return nil | |||
switch cmd.Scene { | |||
case "pullUp", "standJump", "sitUps": | |||
if len(cmd.CameraUrls) < 1 { | |||
return errors.New("cameraUrls can not less than 1") | |||
} | |||
case "race": | |||
if len(cmd.CameraUrls) < 2 { | |||
return errors.New("cameraUrls can not less than 2") | |||
} | |||
default: | |||
return errors.New("unknown scene type:" + cmd.Scene) | |||
} | |||
if u, e := url.Parse(cmd.PushUrl); nil != e { | |||
return errors.New("invalid pushUrl:" + e.Error()) | |||
} else if u.Scheme != "http" && u.Scheme != "https" { | |||
return errors.New("can not support pushUrl with " + u.Scheme) | |||
} | |||
return nil | |||
} | |||
func setScene(c *fiber.Ctx) error { | |||
var sceneCmd SceneCommand | |||
if err := c.BodyParser(&sceneCmd); nil != err { | |||
return failureResponse(c, "-1", err.Error(), 400) | |||
} else if nil != currentScene { | |||
return failureResponse(c, "1", "A working scene is started", 400) | |||
} else if err = validateSceneCmd(sceneCmd); nil != err { | |||
return failureResponse(c, "2", err.Error(), 400) | |||
} else { | |||
currentScene = &sceneCmd | |||
return successResponse(c, "Updated successfully.") | |||
} | |||
var sceneCmd SceneCommand | |||
if err := c.BodyParser(&sceneCmd); nil != err { | |||
return failureResponse(c, "-1", err.Error(), 400) | |||
} else if nil != currentScene { | |||
return failureResponse(c, "1", "A working scene is started", 400) | |||
} else if err = validateSceneCmd(sceneCmd); nil != err { | |||
return failureResponse(c, "2", err.Error(), 400) | |||
} else { | |||
// currentScene = &sceneCmd | |||
if e := sceneTaskProc(&sceneCmd); nil != e { | |||
return failureResponse(c, "3", err.Error(), 409) | |||
} else { | |||
return successResponse(c, "Updated successfully.") | |||
} | |||
} | |||
} | |||
func stopScene(c *fiber.Ctx) error { | |||
currentScene = nil | |||
return successResponse(c, "Updated successfully.") | |||
currentScene = nil | |||
sceneStopChannel <- true | |||
return successResponse(c, "Updated successfully.") | |||
} | |||
func getStatus(c *fiber.Ctx) error { | |||
var scene = "" | |||
var seq = 0 | |||
if nil != currentScene { | |||
scene = currentScene.Scene | |||
} | |||
if nil != currentTest { | |||
seq = currentTest.SequenceId | |||
} | |||
return successResponseEx(c, "success", scene, seq) | |||
var scene = "" | |||
var seq int64 = 0 | |||
if nil != currentScene { | |||
scene = currentScene.Scene | |||
} | |||
if nil != currentTest { | |||
seq = currentTest.SequenceId | |||
} | |||
return successResponseEx(c, "success", scene, seq) | |||
} | |||
func sceneTaskProc(cmd *SceneCommand) error { | |||
var f func(int64) error = nil | |||
switch cmd.Scene { | |||
case "pullUp": | |||
f = pullUpTask | |||
case "standJump": | |||
f = standJumpTask | |||
case "sitUps": | |||
f = sitUpsTask | |||
case "race": | |||
f = raceTask | |||
default: | |||
return errors.New("unknown scene type:" + cmd.Scene) | |||
} | |||
sceneStopChannel = make(chan bool) | |||
var tk = time.NewTicker(time.Second * 3) | |||
go func() { | |||
defer func() { | |||
tk.Stop() | |||
close(sceneStopChannel) | |||
sceneStopChannel = nil | |||
}() | |||
time.Sleep(time.Second) | |||
currentScene = cmd | |||
currentScene.proc = f | |||
for { | |||
select { | |||
case <-tk.C: | |||
log.Println(" ...") | |||
case <-sceneStopChannel: | |||
log.Println("Scene Stopping...") | |||
return | |||
} | |||
} | |||
}() | |||
return nil | |||
} | |||
func init() { | |||
currentScene = nil | |||
currentScene = nil | |||
sceneStopChannel = nil | |||
} |