mirror of
https://github.com/kikito/lua-sandbox.git
synced 2024-12-18 03:04:20 +00:00
added refs param
This commit is contained in:
parent
ee9c0f9164
commit
36fb0929e0
11
README.md
11
README.md
@ -34,6 +34,17 @@ Usage
|
|||||||
-- It is also possible to use the env option to add additional variables to the environment
|
-- It is also possible to use the env option to add additional variables to the environment
|
||||||
sandbox('return foo', {env = {foo = 'This was on the environment'}})
|
sandbox('return foo', {env = {foo = 'This was on the environment'}})
|
||||||
|
|
||||||
|
-- The variables defined on the env are deep-copied and changes on them will not be persisted
|
||||||
|
local env = {foo = "can't touch this"}
|
||||||
|
sandbox('foo = "bar"', {env = env})
|
||||||
|
assert(env.foo = "can't touch this")
|
||||||
|
|
||||||
|
-- If you want to modify variables from inside the sandbox, use the refs option:
|
||||||
|
local refs = {foo = "kindof insecure"}
|
||||||
|
sandbox('foo = "changed"', {refs = refs})
|
||||||
|
assert(refs.foo = "changed")
|
||||||
|
|
||||||
|
|
||||||
Installation
|
Installation
|
||||||
============
|
============
|
||||||
|
|
||||||
|
@ -67,9 +67,10 @@ copy = function(other)
|
|||||||
end
|
end
|
||||||
|
|
||||||
|
|
||||||
local function cleanup()
|
local function cleanup(sandboxed_env, refs)
|
||||||
debug.sethook()
|
debug.sethook()
|
||||||
string.rep = string_rep
|
string.rep = string_rep
|
||||||
|
for k,_ in pairs(refs) do refs[k] = sandboxed_env[k] end
|
||||||
end
|
end
|
||||||
|
|
||||||
local function run(f, options)
|
local function run(f, options)
|
||||||
@ -79,8 +80,10 @@ local function run(f, options)
|
|||||||
|
|
||||||
local quota = options.quota or 500000
|
local quota = options.quota or 500000
|
||||||
local env = options.env or {}
|
local env = options.env or {}
|
||||||
|
local refs = options.refs or {}
|
||||||
|
|
||||||
local sandboxed_env = merge(copy(BASE_ENV), env)
|
local sandboxed_env = merge(copy(BASE_ENV), env)
|
||||||
|
for k,v in pairs(refs) do sandboxed_env[k] = v end
|
||||||
|
|
||||||
setfenv(f, sandboxed_env)
|
setfenv(f, sandboxed_env)
|
||||||
|
|
||||||
@ -93,7 +96,7 @@ local function run(f, options)
|
|||||||
local timeout = function(str)
|
local timeout = function(str)
|
||||||
instructions_count = instructions_count + 1
|
instructions_count = instructions_count + 1
|
||||||
if instructions_count >= quota then
|
if instructions_count >= quota then
|
||||||
cleanup()
|
cleanup(sandboxed_env, refs)
|
||||||
error('Quota exceeded: ' .. tostring(instructions_count) .. '/' .. tostring(quota) .. ' instructions')
|
error('Quota exceeded: ' .. tostring(instructions_count) .. '/' .. tostring(quota) .. ' instructions')
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
@ -102,7 +105,7 @@ local function run(f, options)
|
|||||||
|
|
||||||
local ok, result = pcall(f)
|
local ok, result = pcall(f)
|
||||||
|
|
||||||
cleanup()
|
cleanup(sandboxed_env, refs)
|
||||||
|
|
||||||
if not ok then error(result) end
|
if not ok then error(result) end
|
||||||
return result
|
return result
|
||||||
|
@ -58,19 +58,49 @@ describe('sandbox', function()
|
|||||||
|
|
||||||
it('accepts a quota param', function()
|
it('accepts a quota param', function()
|
||||||
assert.no_has_error(function() sandbox("for i=1,100 do end") end)
|
assert.no_has_error(function() sandbox("for i=1,100 do end") end)
|
||||||
assert.has_error(function() sandbox("for i=1,100 do end", {quota = 50}) end)
|
assert.has_error(function() sandbox("for i=1,100 do end", {quota = 20}) end)
|
||||||
end)
|
end)
|
||||||
|
|
||||||
end)
|
end)
|
||||||
|
|
||||||
describe('when given an env', function()
|
describe('when given an env option', function()
|
||||||
it('is available on the sandboxed env', function()
|
it('is available on the sandboxed env', function()
|
||||||
assert.equal(1, sandbox("return foo", {env = {foo = 1}}))
|
assert.equal(1, sandbox("return foo", {env = {foo = 1}}))
|
||||||
end)
|
end)
|
||||||
|
|
||||||
it('does not hide previous env', function()
|
it('does not hide base env', function()
|
||||||
assert.equal('HELLO', sandbox("return string.upper(foo)", {env = {foo = 'hello'}}))
|
assert.equal('HELLO', sandbox("return string.upper(foo)", {env = {foo = 'hello'}}))
|
||||||
end)
|
end)
|
||||||
|
|
||||||
|
it('can not modify the env', function()
|
||||||
|
local env = {foo = 1}
|
||||||
|
sandbox("foo = 2", {env = env})
|
||||||
|
assert.equal(env.foo, 1)
|
||||||
|
end)
|
||||||
|
end)
|
||||||
|
|
||||||
|
describe('when given a refs option', function()
|
||||||
|
it('is available on the sandboxed env', function()
|
||||||
|
assert.equal(1, sandbox("return foo", {refs = {foo = 1}}))
|
||||||
|
end)
|
||||||
|
|
||||||
|
it('does not hide base env', function()
|
||||||
|
assert.equal('HELLO', sandbox("return string.upper(foo)", {refs = {foo = 'hello'}}))
|
||||||
|
end)
|
||||||
|
|
||||||
|
it('can modify the refs', function()
|
||||||
|
local refs = {foo = 1}
|
||||||
|
sandbox("foo = 2", {refs = refs})
|
||||||
|
assert.equal(refs.foo, 2)
|
||||||
|
end)
|
||||||
|
|
||||||
|
it('can modify the ref tables keys', function()
|
||||||
|
local refs = {items = {quantity = 1}}
|
||||||
|
sandbox("items.quantity = 2", {refs = refs})
|
||||||
|
assert.equal(refs.items.quantity, 2)
|
||||||
|
end)
|
||||||
|
|
||||||
|
|
||||||
end)
|
end)
|
||||||
|
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user