zoukankan      html  css  js  c++  java
  • 关于lua 5.3 服务端热更新流程

    脚本的热更新的流程都大同小异, 第一步先保存旧代码的块的数据, 第二部加载新的代码块,第三步将旧代码块的局部和全局数据拷贝到新代码块的对应的

    变量中。

    在服务器热更新中,主要考虑热更的内容是什么, 一般更新分两种,一种是逻辑的更新,一种是变量的值更新。

    先谈论第一种,在lua 5.3中,继承了新的debug.upvaluejoin(f1, i, f2, j)函数,能将函数f1的第i个个upvalue引用f2的第j个upvalue, 

    可以通过debug.getupvalue函数,获取ENV 的upvalue来的索引位置,找到该位置后,可以通过debug.upvaluejoin函数来实现env的交换。

    第二种就是要更新变量值,lua中的变量值更新,除了table外,其它变量类型都可以通过直接赋值来改变值的大小。由于table的回收,会导致其它引用

    该table的变量都会收到影响,会导致错误的发生,所以, table的值更新,不能通过直接赋值, 可以通过移除table里面的所有元素的值,table的table除外,

    然后将新table的所有元素的值遍历赋值给旧的table,注意的是不能将table也赋值,如果新table里有新的子元素是table类型,必须要在旧table对应值里重新

    创建一个新的table,递归将值拷贝。

    以下是table的拷贝方法实现热更的过程:

    HotFixTable = {}
    
    -- copy a old table's all key and value  to new table, but don't release old table
    local function copyTable( oldTbl, newTbl)
        for k, v in pairs(newTbl) do
            if type(v) == "table" then
                if type(oldTbl[k]) ~= "table" then
                    oldTbl[k] = {}
                end
                copyTable( oldTbl[k], v)
            else
                oldTbl[k] = v
            end
        end
        return oldTbl, newTbl    
    end
    
    --table no need release
    local function clearTable(tbl)
        for k, v in pairs(tbl) do
            if type(v) ~= "table" then
                tbl[k] = nil
            else
                clearTable(v)
            end
        end
    
        return tbl
    end
    
    --use file to hotfix the source table
    function HotFixTable.hotFixByFileName(fileName, sourceTbl)
        local deskTbl
        local function newIndexFunc(tbl, name, value)--t:table, name:key, f:function
            deskTbl = value
        end
    
        local dummy_env = setmetatable({}, { __newindex = newIndexFunc })
        local f, err = loadfile(fileName, "bt", dummy_env)
        if f then
            local ok, err = pcall(f)
            assert(ok, err)
            if ok then
                clearTable(sourceTbl)
                copyTable(sourceTbl, deskTbl)
            end
        end
    end
    
    --use lua string to hotfix the table
    function HotFixTable.hotFixByData(hitfixContent, sourceTbl)
        local deskTbl
        local function newIndexFunc(tbl, name, value)--t:table, name:key, f:function
            deskTbl = value
        end
    
        local dummy_env = setmetatable({}, { __newindex = newIndexFunc })
        local f, err = load(hitfixContent, "=patch", "bt", dummy_env)
        if f then
            local ok, err = pcall(f)
            assert(ok, err)
            if ok then
                clearTable(sourceTbl)
                copyTable(sourceTbl, deskTbl)
            end
        end
    end

    调用方法如下:

    HotFixTable.hotFixByFileName("新table的保存所在文件", 旧table)
  • 相关阅读:
    【Feature】使用Feature导入WebPart
    千万别动SharePoint数据库
    【PS】使用PowerShell创建WinForm程序(转载)
    【WebServices】调用 SharePoint WebServices 注意事项
    【转载】十一种Web网站程序性能测试工具介绍
    【List Event Receivers】区分自定义“事件处理”功能的两种部署方式
    [转] SharePoint Server 2007 页面模型
    第一天 从此在这记录学习C++的点点滴滴
    《C++ Primer》第7章 函数
    Emacs 自动填充头文件
  • 原文地址:https://www.cnblogs.com/HemJohn/p/5907635.html
Copyright © 2011-2022 走看看