Estoy tratando de usar archivos Lua sin procesar para fines de configuración, pero no quiero que los archivos de configuración contaminen el espacio de nombres global.Alcance variable de Lua con setfenv
El problema al que me estoy enfrentando es que dofile
siempre parece ejecutarse en el entorno global real, por lo que los archivos externos simplemente lanzan todas sus declaraciones a _G.
Aquí hay un archivo principal de ejemplo, con comentarios que indican mis deseos.
function myFunc()
print("In the sandbox:")
print("Should be 1:", a) -- falls back to _G for lookup
a = 2 -- instantiating new global for sandbox
print("Should be 2:", a) -- from sandbox
print("Should still be 1:", _G.a) -- from host environment
dofile("loading.lua") -- here's where things go wrong
print "\nBack in the sandbox:"
print("Should be 3:", a) -- changed by loadfile
print("Should STILL be 1:", _G.a) -- unchanged
end
a = 1
local newgt = {} -- new environment
setmetatable(newgt, {__index = _G})
setfenv(myFunc, newgt)
myFunc()
print("\nOutside of the sandbox:")
print("Should be 1: ", a) -- in theory, has never changed
y el archivo se carga (loading.lua
:
print ("\nLoading file...")
print("Should be 2: ", a) -- coming from the sandbox environment
a = 3
print("Should be 3: ", a) -- made a change to the environment
Y, finalmente, la salida que estoy viendo:
In the sandbox:
Should be 1: 1
Should be 2: 2
Should still be 1: 1
Loading file...
Should be 2: 1
Should be 3: 3
Back in the sandbox:
Should be 3: 2
Should STILL be 1: 3
Outside of the sandbox:
Should be 1: 3
Está imprimiendo el literal 1 en lugar del valor de a. Si se trata de un trabajo de cortar y pegar, entonces su código es incorrecto, por lo que está viendo esa angustiosa línea final. –
¡Ja! Gracias, el dedo gordo es el culpable de al menos el final. Gracias por la captura. – SJML