HomeServer/lualib-src/Server-main/Common/Player/DBData.lua
2024-11-20 15:41:37 +08:00

137 lines
5.0 KiB
Lua
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

local skynet = require "skynet"
local oo = require "Class"
local log = require "Log"
local DBData = oo.class()
--检查下是不是有新增的字段
function DBData:CheckNewFields( newTable , initTable)
for key, value in pairs( initTable ) do
if "table" ~= type( value[2] ) then
--非表,如果未给值就必须初始化
if nil == newTable[ value[1] ] then
newTable[value[1] ] = value[2]
end
else
--是表,如果未给值必须初始化
if nil == newTable[ value[1] ] then
newTable[ value[1] ] = {}
end
--遍历子结点
self:CheckNewFields( newTable[ value[1] ] , value[2] )
end
end
end
--遍历用户数据
function DBData:Traversal(newData , oldData)
for key, value in pairs(oldData) do
if "table" ~= type(value[2]) then
newData[value[1]] = value[2]
else
newData[value[1]] = {}
newData[value[1]] = self:Parse( newData[value[1]] , value[1] ,value[2] )
end
end
end
--解析字段
function DBData:Parse( newTable , t1 ,v2 )
if "table" ~= type(v2) then
newTable[t1] =v2
else
for key, value in pairs(v2) do
if "table" ~= type(value[2]) then
newTable[ value[1] ] = value[2]
else
newTable[ value[1] ]= {}
newTable[ value[1] ] = self:Parse(newTable[value[1]] , value[1] , value[2])
end
end
end
return newTable
end
--[[
--需要在这里增加更新玩家字段
function DBData:CheckUserVision( log )
--[[
新增字段事例
table.insert(updateData , {"test1",0 }) test1为不存在的字段名默认类型为0
table.insert(updateData , {"test2",{} }) test2为不存在的字段名默认类型为
table.insert(updateData , {"test3",{ a = 1 ,b = 2} }) test3为存在的字段名test3是表在test3新增a,b字段
--这里添加每个更新版本的玩家字段
local updateData = {}
local sql = ""
self:UpdateDBData( updateData , log )
end
--更新新字段到数据库
function DBData:UpdateDBData(updateData ,log)
log.info("开始更新新字段到数据库")
local newData = {}
local t1 = skynet.GetTime()
self:Traversal(newData , updateData)
--得到数据库中所有玩家数量
local sql = string.format("select count(1) from player" )
local queryData = skynet.server.db:Query(sql)
local id = nil
local userInfo = nil
local jsonInfo = nil
local modifyCount = 0
if #queryData > 0 then
--一次取出太多的数据在内存中,底层会警告,为了更稳固,所以分批读取用户数据进行处理
local curUserCount = tonumber(queryData[1]["count(1)"])
local queryMaxUser = 1000 --每次从数据库中取出玩家数据的数量
local startId = 100000 --帐号的起始ID
local endId = startId + curUserCount --帐号的结束ID
local startPos = 0
local endPos = 0
log.info("数据库总共玩家数量", curUserCount)
for pos = startId, endId , queryMaxUser do
startPos = pos
endPos = startPos + (queryMaxUser - 1)
if endPos > endId then
--如果大于结束ID就获取最终的结束ID
endPos = (startPos + ( endId - startPos)) - 1
end
--根据ID获取用户信息
sql = string.format("select id,data from player where id >= %d and id <= %d",startPos ,endPos )
queryData = skynet.server.db:Query(sql)
log.info(string.format("当前起始ID %d 结束ID %d 的范围 取出数量 %d ",startPos ,endPos , #queryData))
for i = 1, #queryData do
id = tonumber(queryData[i]["id"])
userInfo = queryData[i]["data"]
if userInfo then
jsonInfo = JSON:decode(userInfo)
for key, value in pairs(newData) do
if jsonInfo[ key ] then
for k, v in pairs(value) do
jsonInfo[ key ][ k ] = v
end
else
jsonInfo[ key ] = value
end
end
sql = string.format("update player set data = '%s' where id = %d", JSON:encode(jsonInfo), id)
skynet.server.db:Query(sql)
modifyCount = modifyCount + 1
end
end
end
end
log.info("更新完所有用户需要的时间",skynet.GetTime() - t1, "秒")
log.info("成功修改玩家数量",modifyCount)
log.info("结束更新新字段到数据库")
end
]]
skynet.server.dbData = DBData
return DBData