feat: validate Worker protocol and verify process crash recovery
This commit is contained in:
@@ -10,6 +10,7 @@ import (
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"git.yuntuo.hk/k2safe/orbit/internal/testcontract"
|
||||
"git.yuntuo.hk/k2safe/orbit/internal/transport/httpserver"
|
||||
core "git.yuntuo.hk/k2safe/orbit/model"
|
||||
pulse "git.yuntuo.hk/k2safe/orbit/pulse/model"
|
||||
@@ -75,6 +76,7 @@ func (c *testWorkerSocket) send(kind string, body any, id core.ID) core.ID {
|
||||
if err != nil {
|
||||
c.t.Fatal(err)
|
||||
}
|
||||
testcontract.WorkerFrame(c.t, "client", frame)
|
||||
ctx, cancel := context.WithTimeout(c.ctx, 5*time.Second)
|
||||
defer cancel()
|
||||
if err := c.conn.Write(ctx, websocket.MessageText, frame); err != nil {
|
||||
@@ -90,6 +92,7 @@ func (c *testWorkerSocket) read() testWorkerFrame {
|
||||
if err != nil {
|
||||
c.t.Fatal(err)
|
||||
}
|
||||
testcontract.WorkerFrame(c.t, "server", raw)
|
||||
var frame testWorkerFrame
|
||||
if kind != websocket.MessageText || json.Unmarshal(raw, &frame) != nil || frame.Version != "1" || frame.MessageID.Validate() != nil {
|
||||
c.t.Fatal("invalid server frame")
|
||||
@@ -191,6 +194,10 @@ func TestIntegrationWorkerWebSocket(t *testing.T) {
|
||||
if err := json.Unmarshal(first.ack(startMessage), &begun); err != nil || !begun.Lease.Active || begun.Lease.State != pulse.AttemptRunning {
|
||||
t.Fatal("missing durable start")
|
||||
}
|
||||
var renewed worker.CommandResult
|
||||
if err := json.Unmarshal(first.ack(first.send("task.renew", ref, "")), &renewed); err != nil || !renewed.Lease.Active {
|
||||
t.Fatal("missing renewal confirmation")
|
||||
}
|
||||
// 模拟旧节点连接断开;新的 WSS 连接进入不同节点并原子迁移有效尝试。
|
||||
_ = first.conn.CloseNow()
|
||||
second := connectTestWorker(t, ctx, serverB, fixture)
|
||||
@@ -220,13 +227,22 @@ func TestIntegrationWorkerWebSocket(t *testing.T) {
|
||||
})
|
||||
t.Run("strict_worker_frame_and_hub_shutdown", func(t *testing.T) {
|
||||
conn := connectTestWorker(t, ctx, serverB, fixture)
|
||||
secret, _, err := worker.NewSecret()
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
message := conn.send("worker.resume", worker.AttemptRef{TaskID: executionID(t), AttemptID: executionID(t), Epoch: 1, LeaseSecret: secret}, "")
|
||||
failure := conn.read()
|
||||
if failure.Type != "error" || failure.ReplyTo != message || failure.Error == nil || failure.Error.Code != "NOT_FOUND" {
|
||||
t.Fatal("missing structured error frame")
|
||||
}
|
||||
raw := []byte(`{"protocol_version":"1","protocol_version":"1","type":"worker.capacity"}`)
|
||||
if err := conn.conn.Write(ctx, websocket.MessageText, raw); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
readCtx, stop := context.WithTimeout(ctx, 3*time.Second)
|
||||
defer stop()
|
||||
_, _, err := conn.conn.Read(readCtx)
|
||||
_, _, err = conn.conn.Read(readCtx)
|
||||
if websocket.CloseStatus(err) != websocket.StatusPolicyViolation {
|
||||
t.Fatalf("duplicate frame not rejected: %v", err)
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user