147 lines
6.1 KiB
Go
147 lines
6.1 KiB
Go
package sdkserver
|
|
|
|
import (
|
|
"encoding/base64"
|
|
"encoding/json"
|
|
"net/http"
|
|
"net/http/httptest"
|
|
"os"
|
|
"path/filepath"
|
|
"strings"
|
|
"testing"
|
|
"time"
|
|
|
|
"gac-hkrpg-go/internal/common"
|
|
goproto "gac-hkrpg-go/protocol/proto"
|
|
"google.golang.org/protobuf/proto"
|
|
)
|
|
|
|
func TestLiveBattleReportRoundTripAndExpiry(t *testing.T) {
|
|
configPath := filepath.Join(t.TempDir(), "server.json")
|
|
config := `{"account_name":"fixture","player_uid":52022,"activity_schedule":{"begin_time":0,"end_time":100},"srtool":{"lease_file":"fixture-session.json","lease_seconds":30},"battle_diagnostics":{"live_report_stale_seconds":10},"client_version":"fixture","game_host":"localhost","game_port":32101,"sdk_host":"localhost","sdk_port":32102,"public_game_host":"localhost","public_sdk_url":"http://localhost:32102"}`
|
|
if err := os.WriteFile(configPath, []byte(config), 0600); err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
t.Setenv("GAC_CONFIG", configPath)
|
|
t.Setenv("GAC_LIVE_BATTLE_STALE_SECONDS", "10")
|
|
defer clearLiveBattleReport()
|
|
|
|
statistics := &goproto.BattleStatistics{
|
|
TotalBattleTurns: 2,
|
|
BattleAvatarList: []*goproto.AvatarBattleInfo{{
|
|
Id: 1204, StageId: 1052106, TotalDamage: 400,
|
|
AttackTypeDamage: []*goproto.AttackDamageProperty{{AttackType: "Normal", Damage: 400}},
|
|
}},
|
|
MonsterList: []*goproto.MonsterBattleInfo{{MonsterId: 5035011, TotalDamageTaken: 400}},
|
|
}
|
|
wire, err := proto.Marshal(statistics)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
requestBody, err := json.Marshal(liveBattleReportRequest{
|
|
Active: true, StatisticsBase64: base64.StdEncoding.EncodeToString(wire),
|
|
})
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
post := httptest.NewRequest(http.MethodPost, "/api/battle_report/live", strings.NewReader(string(requestBody)))
|
|
postResponse := httptest.NewRecorder()
|
|
apiBattleReportLive(postResponse, post)
|
|
if postResponse.Code != http.StatusOK {
|
|
t.Fatalf("live POST status = %d, body = %s", postResponse.Code, postResponse.Body.String())
|
|
}
|
|
|
|
getResponse := httptest.NewRecorder()
|
|
apiBattleReport(getResponse, httptest.NewRequest(http.MethodGet, "/api/battle_report", nil))
|
|
var result struct {
|
|
IsLive bool `json:"is_live"`
|
|
Revision int64 `json:"revision"`
|
|
Report common.BattleReport `json:"report"`
|
|
}
|
|
if err := json.Unmarshal(getResponse.Body.Bytes(), &result); err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if !result.IsLive || result.Report.EndStatus != "LIVE" || result.Report.StageID != 1052106 {
|
|
t.Fatalf("unexpected live response: %+v", result)
|
|
}
|
|
if result.Report.TeamTotalDamage != 400 || result.Report.Avatars[0].DamagePercent != 100 || result.Revision == 0 {
|
|
t.Fatalf("unexpected live damage values: %+v", result.Report)
|
|
}
|
|
|
|
avatarSnapshots := []*goproto.AvatarBattleInfo{
|
|
{
|
|
Id: 1409, StageId: 1052106, TotalDamage: 600, TotalTurns: 2,
|
|
AttackTypeDamage: []*goproto.AttackDamageProperty{{AttackType: "BPSkill", Damage: 600}},
|
|
},
|
|
{
|
|
Id: 1507, StageId: 1052106, TotalDamage: 400, TotalTurns: 1,
|
|
AttackTypeDamage: []*goproto.AttackDamageProperty{{AttackType: "Normal", Damage: 400}},
|
|
},
|
|
}
|
|
avatarStatisticsBase64 := make([]string, 0, len(avatarSnapshots))
|
|
for _, avatar := range avatarSnapshots {
|
|
wire, err := proto.Marshal(avatar)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
avatarStatisticsBase64 = append(avatarStatisticsBase64, base64.StdEncoding.EncodeToString(wire))
|
|
}
|
|
requestBody, err = json.Marshal(liveBattleReportRequest{
|
|
Active: true,
|
|
AvatarStatisticsBase64: avatarStatisticsBase64,
|
|
TotalBattleTurns: 3,
|
|
})
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
post = httptest.NewRequest(http.MethodPost, "/api/battle_report/live", strings.NewReader(string(requestBody)))
|
|
postResponse = httptest.NewRecorder()
|
|
apiBattleReportLive(postResponse, post)
|
|
if postResponse.Code != http.StatusOK {
|
|
t.Fatalf("avatar snapshot POST status = %d, body = %s", postResponse.Code, postResponse.Body.String())
|
|
}
|
|
|
|
getResponse = httptest.NewRecorder()
|
|
apiBattleReport(getResponse, httptest.NewRequest(http.MethodGet, "/api/battle_report", nil))
|
|
if err := json.Unmarshal(getResponse.Body.Bytes(), &result); err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if !result.IsLive || result.Report.TotalBattleTurns != 3 || result.Report.TeamTotalDamage != 1000 {
|
|
t.Fatalf("unexpected avatar-only live report: %+v", result)
|
|
}
|
|
if len(result.Report.Avatars) != 2 || result.Report.Avatars[0].DamagePercent != 60 || result.Report.Avatars[1].DamagePercent != 40 {
|
|
t.Fatalf("unexpected avatar-only live shares: %+v", result.Report.Avatars)
|
|
}
|
|
if result.Report.Avatars[0].AttackTypeDamage["BPSkill"] != 600 || result.Report.Avatars[1].AttackTypeDamage["Normal"] != 400 {
|
|
t.Fatalf("unexpected avatar-only live breakdown: %+v", result.Report.Avatars)
|
|
}
|
|
servantWire, _ := proto.Marshal(&goproto.BattleAvatarServantInfo{AvatarId: avatarSnapshots[1].Id, EntityId: 88, TotalDamage: 1000})
|
|
requestBody, _ = json.Marshal(liveBattleReportRequest{
|
|
Active: true, AvatarStatisticsBase64: avatarStatisticsBase64,
|
|
ServantStatisticsBase64: []string{base64.StdEncoding.EncodeToString(servantWire)},
|
|
ServantBreakdowns: []liveAvatarBreakdown{{Damage: map[string]float64{"BPSkill": 900}}},
|
|
})
|
|
postResponse = httptest.NewRecorder()
|
|
apiBattleReportLive(postResponse, httptest.NewRequest(http.MethodPost, "/api/battle_report/live", strings.NewReader(string(requestBody))))
|
|
if postResponse.Code != http.StatusOK {
|
|
t.Fatalf("servant POST: %s", postResponse.Body.String())
|
|
}
|
|
getResponse = httptest.NewRecorder()
|
|
apiBattleReport(getResponse, httptest.NewRequest(http.MethodGet, "/api/battle_report", nil))
|
|
if err := json.Unmarshal(getResponse.Body.Bytes(), &result); err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
owner := result.Report.Avatars[1]
|
|
if !result.IsLive || result.Report.TeamTotalDamage != 2000 || owner.TotalDamage != 1400 || owner.MemospriteDamage != 1000 ||
|
|
owner.DamagePercent != 70 || owner.AttackTypeDamage["BPSkill"] != 900 {
|
|
t.Fatalf("servant data lost through live API: report=%+v owner=%+v", result.Report, owner)
|
|
}
|
|
|
|
liveBattleReportState.Lock()
|
|
liveBattleReportState.received = time.Now().Add(-11 * time.Second)
|
|
liveBattleReportState.Unlock()
|
|
if _, _, live, err := latestLiveBattleReport(); err != nil || live {
|
|
t.Fatalf("expired live report should be ignored, live=%t err=%v", live, err)
|
|
}
|
|
}
|