Files
90CNServer/server/internal/modules/dnf/inventory/handler_amplify_test.go
T
hanfuit 645b64fe21 DNF90 服务端与启动器完整源码(含 GM 工具功能增强)
服务端(Go):
- GM 塞背包/带属性装备发放:在线角色推送 op14 增量物品行,背包实时刷新,无需回角色选择界面
- GM 改金币/改等级:去掉在线拒绝,落库后推送 op14 钱包/op37 等级状态,在线实时刷新
- 等级端点统一切换到新版 GMSetCharacterLevel(自带在线刷新)
- 无限/锁死疲劳模式 + 燃烧疲劳:每房间消耗 2 点、打怪与通关经验双倍
- 燃烧疲劳开关时给所有在线角色推送系统提示(op12 mode 0)
- 深渊史诗掉率:GM 全局倍率 + 城镇增益药剂窗口倍率,真实接入掉落结算

启动器(Python/JS):
- 标题栏自绘、窗口 1204x717、禁止拖拽改大小、仅最小化/关闭
- GM 工具:疲劳与燃烧、深渊史诗掉率、拍卖行上架(单一定价对齐)
- 拍卖行上架前端对齐服务端单一价格语义,修复 400 报错
2026-11-04 14:31:55 +08:00

102 lines
4.1 KiB
Go

package inventory
import (
"bytes"
"context"
"encoding/binary"
"testing"
"longheng.io/server/internal/modules/dnf/alignedcmd"
"longheng.io/server/internal/modules/dnf/dnfenum"
dnfrepo "longheng.io/server/internal/modules/dnf/repository"
dnfrepomemory "longheng.io/server/internal/modules/dnf/repository/memory"
)
func purifyRequestBody(targetSlot int16, targetItem int32, materialSlot int16, materialItem int32) []byte {
body := make([]byte, 12)
binary.LittleEndian.PutUint16(body[0:2], uint16(targetSlot))
binary.LittleEndian.PutUint32(body[2:6], uint32(targetItem))
binary.LittleEndian.PutUint16(body[6:8], uint16(materialSlot))
binary.LittleEndian.PutUint32(body[8:12], uint32(materialItem))
return body
}
func investRequestBody(action byte, targetSlot int16, targetItem int32, materialSlot int16, materialItem int32, selected byte, name string) []byte {
body := make([]byte, 14)
body[0] = action
binary.LittleEndian.PutUint16(body[1:3], uint16(targetSlot))
binary.LittleEndian.PutUint32(body[3:7], uint32(targetItem))
binary.LittleEndian.PutUint16(body[7:9], uint16(materialSlot))
binary.LittleEndian.PutUint32(body[9:13], uint32(materialItem))
body[13] = selected
if action == investAmplifyActionPureGold {
length := make([]byte, 4)
binary.LittleEndian.PutUint32(length, uint32(len(name)))
body = append(body, length...)
body = append(body, name...)
}
return body
}
func handleAmplifyRequest(t *testing.T, repos dnfrepo.Group, opcode dnfenum.CmdPacket, body []byte, resolver alignedcmd.AmplifyItemResolver) alignedcmd.Result {
t.Helper()
result, err := NewHandler().Handle(context.Background(), alignedcmd.Request{
Opcode: uint16(opcode),
Body: body,
SelectedCharacterID: 77,
Repositories: repos,
AmplifyItemResolver: resolver,
})
if err != nil {
t.Fatal(err)
}
return result
}
func TestHandlerAmplifySuccessUsesOnlySelfContainedACK(t *testing.T) {
ctx := context.Background()
t.Run("op204", func(t *testing.T) {
repos := dnfrepomemory.NewMemoryGroup()
saveAmplifyFixture(t, ctx, repos, unidentifiedAmplifyFlag, 0, 0, 1183, 1)
resolution := validAmplifyResolution()
resolution.PurifyMaterialCount = 1
got := handleAmplifyRequest(t, repos, dnfenum.CmdPacketPurifyItem, purifyRequestBody(9, 700, 12, 1183), staticAmplifyResolver(resolution))
if !got.Handled || !got.ResponseAllowed || len(got.UpperResponses) != 1 || len(got.PostActions) != 0 {
t.Fatalf("result = %+v", got)
}
ack := got.UpperResponses[0]
if ack.Classification != 1 || ack.MsgID != uint16(dnfenum.CmdPacketPurifyItem) || len(ack.Body) != 12 || ack.Body[0] != 1 {
t.Fatalf("ACK = %+v", ack)
}
})
t.Run("op205 Pure Gold", func(t *testing.T) {
repos := dnfrepomemory.NewMemoryGroup()
saveAmplifyFixture(t, ctx, repos, 1, 7, 0, 8238, 1)
resolution := validAmplifyResolution()
resolution.PureGoldOption = amplifyOptionAll
resolution.PureGoldMaterialCount = 1
resolution.PureGoldLevels = []alignedcmd.AmplifyWeightedLevel{{Level: 7, Weight: 1}}
got := handleAmplifyRequest(t, repos, dnfenum.CmdPacketInvestItemAmplifyOption, investRequestBody(2, 9, 700, 12, 8238, 4, "target"), staticAmplifyResolver(resolution))
if !got.Handled || !got.ResponseAllowed || len(got.UpperResponses) != 1 || len(got.PostActions) != 0 {
t.Fatalf("result = %+v", got)
}
ack := got.UpperResponses[0]
if ack.Classification != 1 || ack.MsgID != uint16(dnfenum.CmdPacketInvestItemAmplifyOption) || len(ack.Body) != 14 || ack.Body[0] != 1 || ack.Body[13] != 7 {
t.Fatalf("ACK = %+v", ack)
}
})
}
func TestHandlerAmplifyFailuresReturnProvenErrorEnvelopes(t *testing.T) {
repos := dnfrepomemory.NewMemoryGroup()
got := handleAmplifyRequest(t, repos, dnfenum.CmdPacketPurifyItem, []byte{1, 2}, nil)
if len(got.UpperResponses) != 1 || !bytes.Equal(got.UpperResponses[0].Body, []byte{0, 1}) {
t.Fatalf("op204 error result = %+v", got)
}
got = handleAmplifyRequest(t, repos, dnfenum.CmdPacketInvestItemAmplifyOption, []byte{1, 2}, nil)
if len(got.UpperResponses) != 1 || !bytes.Equal(got.UpperResponses[0].Body, []byte{0, investAmplifyErrorInvalid}) {
t.Fatalf("op205 error result = %+v", got)
}
}