必须严格做权限、日志、风控分层 ,不能直接裸改属性值;属性不是简单赋值,要走 AttrMgr 的标准化接口,不然会破坏属性缓存、Buff、装备、套装的联动计算。
1、两种修改模式(区分开)
- 临时属性(增益,下线消失 / 时效,Buff形式) 走 BuffMgr,适合GM临时给无敌、攻速、倍攻这种,不改动角色基础档案。
- 永久基础属性(存库,永久生效) 修改角色基础面板(基础攻击、血量、防御等),属于高危操作,权限必须最高、强制落地日志。
❌ 禁止做法:
ini-- 错误!直接改attr表,会导致属性快照、Buff叠加全部错乱 player.attr.atk = 9999
2、永久属性GM指令示例(attr_set)
lua
--[[
指令:/attr_set 角色名 属性key 值
示例:/attr_set 张三 base_atk 1000
权限:3(最高权限,运营后台专用,禁止普通GM)
依赖:AttrMgr、PlayerMgr、LogMgr
]]
GMMgr:RegisterCmd({
cmd = "attr_set",
perm = 3,
desc = "修改玩家基础永久属性:/attr_set 角色名 attr_key value",
handler = function(gm_player, target_name, attr_key, val_str)
if not target_name or not attr_key or not val_str then
return {ret = -1, msg = "参数错误,用法:/attr_set 角色名 属性名 数值"}
end
local val = tonumber(val_str)
if not val then
return {ret = -2, msg = "属性值必须是数字"}
end
local target = PlayerMgr:GetPlayerByName(target_name)
if not target then
return {ret = -3, msg = "目标玩家不在线"}
end
-- 走属性管理器接口,内部自动重算总属性、同步客户端
local ok, err = AttrMgr:SetBaseAttr(target, attr_key, val)
if not ok then
return {ret = -4, msg = err}
end
AttrMgr:SyncAttr(target)
LogMgr:LogGm(gm_player.uid, "attr_set",
string.format("name:%s,key:%s,val:%d", target_name, attr_key, val),
"GM修改玩家永久基础属性")
return {ret = 0, msg = "属性修改成功"}
end
})
配套 AttrMgr 内部接口示意:
lua
function AttrMgr:SetBaseAttr(player, key, value)
-- 可以在这里加白名单:只允许修改配置里开放的基础属性,拦截total_*总属性
local white_list = {base_hp=true,base_atk=true,base_def=true,base_mp=true}
if not white_list[key] then
return false, "不允许修改该属性"
end
player.base_attr[key] = value
self:RecalcAttr(player) -- 重新计算:基础+装备+buff → 总属性
return true
end
3、临时属性(无敌/倍攻这类,推荐用Buff方案)
ini
-- /add_buff 角色名 buffid 秒数
GMMgr:RegisterCmd({
cmd = "add_buff",
perm = 3,
desc = "给玩家添加临时Buff属性",
handler = function(gm_player, target_name, buffid_str, time_str)
local buff_id = tonumber(buffid_str)
local time = tonumber(time_str) or 60
local target = PlayerMgr:GetPlayerByName(target_name)
if not target then
return {ret = -1, msg = "目标不在线"}
end
BuffMgr:AddBuff(target, buff_id, time)
LogMgr:LogGm(gm_player.uid, "add_buff", target_name..","..buff_id, "GM添加Buff临时属性")
return {ret = 0, msg = "Buff添加成功"}
end
})
4、风控红线(重点)
- 白名单限制 :只能修改
base_*基础属性,禁止直接修改total_hp / total_atk这类最终总属性;总属性是计算结果,不能直接赋值。 - 权限隔离:改永久属性的指令权限 perm=3,和刷物品、沙巴克同等级,普通测试GM不给这个权限。
- 日志必须完整:操作人、目标、属性key、旧值、新值,最好存独立gm_operate流水表,可审计回滚。
- 可选增加二次确认:后台使用时,高危指令增加确认弹窗,避免手滑输错数值。
- 离线玩家兼容扩展:如果需要修改离线角色基础属性,要走DB加载角色数据,修改base_attr字段入库,上线时重新计算属性。
5、对比小结
- 临时效果(无敌、倍数、限时加成)👉 用
add_buff - 永久基础面板调整(调基础攻防)👉 用
attr_set,走AttrMgr、严格白名单审计 - 绝对禁止:直接修改最终总属性
如果你需要,我可以一并写查询玩家属性指令 / 回滚属性指令。