Rewrite lua_eval result processing
This commit is contained in:
parent
cb66ca9741
commit
1b5c81679e
|
@ -6,6 +6,7 @@ local url = 'http://127.0.0.1:4343/'
|
||||||
local tasks = {}
|
local tasks = {}
|
||||||
local filters = {}
|
local filters = {}
|
||||||
local ycounts = {}
|
local ycounts = {}
|
||||||
|
local coparams = {}
|
||||||
|
|
||||||
ws = http.websocket(url..'ws/')
|
ws = http.websocket(url..'ws/')
|
||||||
if ws == false then
|
if ws == false then
|
||||||
|
@ -117,12 +118,13 @@ while true do
|
||||||
ws_send{
|
ws_send{
|
||||||
action='task_result',
|
action='task_result',
|
||||||
task_id=msg.task_id,
|
task_id=msg.task_id,
|
||||||
result={fn()},
|
result={fn(table.unpack(msg.params or {}))},
|
||||||
yields=0,
|
yields=0,
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
tasks[msg.task_id] = coroutine.create(fn)
|
tasks[msg.task_id] = coroutine.create(fn)
|
||||||
ycounts[msg.task_id] = 0
|
ycounts[msg.task_id] = 0
|
||||||
|
coparams[msg.task_id] = msg.params or {}
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
elseif msg.action == 'drop' then
|
elseif msg.action == 'drop' then
|
||||||
|
@ -130,6 +132,7 @@ while true do
|
||||||
tasks[task_id] = nil
|
tasks[task_id] = nil
|
||||||
filters[task_id] = nil
|
filters[task_id] = nil
|
||||||
ycounts[task_id] = nil
|
ycounts[task_id] = nil
|
||||||
|
coparams[task_id] = nil
|
||||||
end
|
end
|
||||||
elseif msg.action == 'sub' then
|
elseif msg.action == 'sub' then
|
||||||
event_sub[msg.event] = true
|
event_sub[msg.event] = true
|
||||||
|
@ -152,7 +155,13 @@ while true do
|
||||||
local del_tasks = {}
|
local del_tasks = {}
|
||||||
for task_id in pairs(tasks) do
|
for task_id in pairs(tasks) do
|
||||||
if filters[task_id] == nil or filters[task_id] == event then
|
if filters[task_id] == nil or filters[task_id] == event then
|
||||||
local r = {coroutine.resume(tasks[task_id], event, p1, p2, p3, p4, p5)}
|
local r
|
||||||
|
if coparams[task_id] ~= nil then
|
||||||
|
r = {coroutine.resume(tasks[task_id], table.unpack(coparams[task_id]))}
|
||||||
|
coparams[task_id] = nil
|
||||||
|
else
|
||||||
|
r = {coroutine.resume(tasks[task_id], event, p1, p2, p3, p4, p5)}
|
||||||
|
end
|
||||||
if coroutine.status(tasks[task_id]) == 'dead' then
|
if coroutine.status(tasks[task_id]) == 'dead' then
|
||||||
ws_send{
|
ws_send{
|
||||||
action='task_result',
|
action='task_result',
|
||||||
|
@ -175,6 +184,7 @@ while true do
|
||||||
tasks[task_id] = nil
|
tasks[task_id] = nil
|
||||||
filters[task_id] = nil
|
filters[task_id] = nil
|
||||||
ycounts[task_id] = nil
|
ycounts[task_id] = nil
|
||||||
|
coparams[task_id] = nil
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -58,6 +58,8 @@ def lua_value(v):
|
||||||
return 'true'
|
return 'true'
|
||||||
if isinstance(v, str):
|
if isinstance(v, str):
|
||||||
return lua_string(v)
|
return lua_string(v)
|
||||||
|
if isinstance(v, bytes):
|
||||||
|
return lua_string(v.decode('latin1'))
|
||||||
if isinstance(v, (int, float)):
|
if isinstance(v, (int, float)):
|
||||||
return str(v)
|
return str(v)
|
||||||
if isinstance(v, list):
|
if isinstance(v, list):
|
||||||
|
|
|
@ -1,6 +1,155 @@
|
||||||
from .errors import LuaException
|
from .errors import LuaException
|
||||||
|
|
||||||
|
|
||||||
|
def lua_table_to_list(x, length: int = None):
|
||||||
|
if not x:
|
||||||
|
return [] if length is None else [None] * length
|
||||||
|
assert all(map(lambda k: isinstance(k, int), x.keys()))
|
||||||
|
assert min(x.keys()) >= 1
|
||||||
|
if length is not None:
|
||||||
|
assert max(x.keys()) <= length
|
||||||
|
else:
|
||||||
|
length = max(x.keys())
|
||||||
|
return [x.get(i + 1) for i in range(length)]
|
||||||
|
|
||||||
|
|
||||||
|
class ResultProc:
|
||||||
|
def __init__(self, result):
|
||||||
|
self._v = result
|
||||||
|
self._i = 1
|
||||||
|
|
||||||
|
def forward(self):
|
||||||
|
self._i += 1
|
||||||
|
|
||||||
|
def back(self):
|
||||||
|
self._i -= 1
|
||||||
|
|
||||||
|
def peek(self):
|
||||||
|
return self._v.get(self._i)
|
||||||
|
|
||||||
|
def take(self):
|
||||||
|
r = self.peek()
|
||||||
|
self.forward()
|
||||||
|
return r
|
||||||
|
|
||||||
|
def take_none(self):
|
||||||
|
x = self.take()
|
||||||
|
assert x is None
|
||||||
|
return x
|
||||||
|
|
||||||
|
def take_bool(self):
|
||||||
|
x = self.take()
|
||||||
|
assert x is True or x is False
|
||||||
|
return x
|
||||||
|
|
||||||
|
def take_int(self):
|
||||||
|
x = self.take()
|
||||||
|
assert isinstance(x, int)
|
||||||
|
assert not isinstance(x, bool)
|
||||||
|
return x
|
||||||
|
|
||||||
|
def take_number(self):
|
||||||
|
x = self.take()
|
||||||
|
assert isinstance(x, (int, float))
|
||||||
|
assert not isinstance(x, bool)
|
||||||
|
return x
|
||||||
|
|
||||||
|
def take_bytes(self):
|
||||||
|
x = self.take()
|
||||||
|
assert isinstance(x, bytes)
|
||||||
|
return x
|
||||||
|
|
||||||
|
def take_string(self):
|
||||||
|
return self.take_bytes().decode('latin1')
|
||||||
|
|
||||||
|
def take_unicode(self):
|
||||||
|
return self.take_bytes().decode('utf-8')
|
||||||
|
|
||||||
|
def take_dict(self, keys=None):
|
||||||
|
x = self.take()
|
||||||
|
assert isinstance(x, dict)
|
||||||
|
if keys is None:
|
||||||
|
return x
|
||||||
|
return TableProc(x, keys)
|
||||||
|
|
||||||
|
def take_list(self, length: int = None):
|
||||||
|
return lua_table_to_list(self.take_dict(), length)
|
||||||
|
|
||||||
|
def check_bool_error(self):
|
||||||
|
success = self.take_bool()
|
||||||
|
if not success:
|
||||||
|
raise LuaException(self.take_string())
|
||||||
|
|
||||||
|
def check_nil_error(self):
|
||||||
|
if self.peek() is None:
|
||||||
|
self.forward()
|
||||||
|
raise LuaException(self.take_string())
|
||||||
|
|
||||||
|
def bool_error_exclude(self, exc_msg):
|
||||||
|
success = self.take_bool()
|
||||||
|
if success:
|
||||||
|
return True
|
||||||
|
msg = self.take_string()
|
||||||
|
if msg == exc_msg:
|
||||||
|
return False
|
||||||
|
raise LuaException(msg)
|
||||||
|
|
||||||
|
def take_option_int(self):
|
||||||
|
if self.peek() is None:
|
||||||
|
return self.take_none()
|
||||||
|
return self.take_int()
|
||||||
|
|
||||||
|
def take_option_bytes(self):
|
||||||
|
if self.peek() is None:
|
||||||
|
return self.take_none()
|
||||||
|
return self.take_bytes()
|
||||||
|
|
||||||
|
def take_option_string(self):
|
||||||
|
if self.peek() is None:
|
||||||
|
return self.take_none()
|
||||||
|
return self.take_string()
|
||||||
|
|
||||||
|
def take_option_unicode(self):
|
||||||
|
if self.peek() is None:
|
||||||
|
return self.take_none()
|
||||||
|
return self.take_unicode()
|
||||||
|
|
||||||
|
def take_option_string_bool(self):
|
||||||
|
p = self.peek()
|
||||||
|
if p is None or p is True or p is False:
|
||||||
|
self.forward()
|
||||||
|
return p
|
||||||
|
return self.take_string()
|
||||||
|
|
||||||
|
def take_list_of_strings(self, length: int = None):
|
||||||
|
x = self.take_list(length)
|
||||||
|
assert all(map(lambda v: isinstance(v, bytes), x))
|
||||||
|
return [v.decode('latin1') for v in x]
|
||||||
|
|
||||||
|
def take_list_of_ints(self):
|
||||||
|
x = self.take_list()
|
||||||
|
assert all(map(lambda v: isinstance(v, int), x))
|
||||||
|
return x
|
||||||
|
|
||||||
|
def take_2d_int(self):
|
||||||
|
x = self.take_list()
|
||||||
|
x = [lua_table_to_list(item) for item in x]
|
||||||
|
for row in x:
|
||||||
|
for item in row:
|
||||||
|
assert isinstance(item, int)
|
||||||
|
return x
|
||||||
|
|
||||||
|
|
||||||
|
class TableProc(ResultProc):
|
||||||
|
def __init__(self, result, keys):
|
||||||
|
self._v = result
|
||||||
|
self._keys = keys
|
||||||
|
self._i = 0
|
||||||
|
|
||||||
|
def peek(self):
|
||||||
|
return self._v.get(self._keys[self._i])
|
||||||
|
|
||||||
|
|
||||||
def coro(result):
|
def coro(result):
|
||||||
assert isinstance(result, list)
|
assert isinstance(result, list)
|
||||||
assert len(result) >= 1
|
assert len(result) >= 1
|
||||||
|
|
|
@ -21,6 +21,8 @@ def serialize(v: Any) -> bytes:
|
||||||
return b'T'
|
return b'T'
|
||||||
elif isinstance(v, (int, float)):
|
elif isinstance(v, (int, float)):
|
||||||
return '[{}]'.format(v).encode(_ENC)
|
return '[{}]'.format(v).encode(_ENC)
|
||||||
|
elif isinstance(v, bytes):
|
||||||
|
return '<{}>'.format(len(v)) + v
|
||||||
elif isinstance(v, str):
|
elif isinstance(v, str):
|
||||||
v = v.encode(_ENC)
|
v = v.encode(_ENC)
|
||||||
return '<{}>'.format(len(v)).encode(_ENC) + v
|
return '<{}>'.format(len(v)).encode(_ENC) + v
|
||||||
|
@ -56,7 +58,7 @@ def _deserialize(b: bytes, _idx: int) -> Tuple[Any, int]:
|
||||||
elif tok == 60: # <
|
elif tok == 60: # <
|
||||||
newidx = b.index(b'>', _idx)
|
newidx = b.index(b'>', _idx)
|
||||||
ln = int(b[_idx:newidx].decode(_ENC))
|
ln = int(b[_idx:newidx].decode(_ENC))
|
||||||
return b[newidx + 1:newidx + 1 + ln].decode(_ENC), newidx + 1 + ln
|
return b[newidx + 1:newidx + 1 + ln], newidx + 1 + ln
|
||||||
elif tok == 123: # {
|
elif tok == 123: # {
|
||||||
r = {}
|
r = {}
|
||||||
while True:
|
while True:
|
||||||
|
@ -67,12 +69,6 @@ def _deserialize(b: bytes, _idx: int) -> Tuple[Any, int]:
|
||||||
key, _idx = _deserialize(b, _idx)
|
key, _idx = _deserialize(b, _idx)
|
||||||
value, _idx = _deserialize(b, _idx)
|
value, _idx = _deserialize(b, _idx)
|
||||||
r[key] = value
|
r[key] = value
|
||||||
if r:
|
|
||||||
for i in range(1, len(r) + 1):
|
|
||||||
if i not in r:
|
|
||||||
break
|
|
||||||
else:
|
|
||||||
r = [r[i + 1] for i in range(len(r))]
|
|
||||||
return r, _idx
|
return r, _idx
|
||||||
else:
|
else:
|
||||||
raise ValueError
|
raise ValueError
|
||||||
|
|
|
@ -25,7 +25,7 @@ class CCApplication(web.Application):
|
||||||
async def _launch_program(self, ws):
|
async def _launch_program(self, ws):
|
||||||
async for msg in self._bin_messages(ws):
|
async for msg in self._bin_messages(ws):
|
||||||
msg = ser.deserialize(msg)
|
msg = ser.deserialize(msg)
|
||||||
if msg['action'] != 'run':
|
if msg[b'action'] != b'run':
|
||||||
await ws.send_bytes(ser.serialize({
|
await ws.send_bytes(ser.serialize({
|
||||||
'action': 'close',
|
'action': 'close',
|
||||||
'error': 'protocol error',
|
'error': 'protocol error',
|
||||||
|
@ -36,9 +36,9 @@ class CCApplication(web.Application):
|
||||||
sys.__stdout__.write('ws send ' + repr(data) + '\n')
|
sys.__stdout__.write('ws send ' + repr(data) + '\n')
|
||||||
asyncio.create_task(ws.send_bytes(data))
|
asyncio.create_task(ws.send_bytes(data))
|
||||||
|
|
||||||
sess = CCSession(msg['computer'], sender)
|
sess = CCSession(msg[b'computer'], sender)
|
||||||
if msg['args']:
|
if msg[b'args']:
|
||||||
sess.run_program(msg['args'][0])
|
sess.run_program(msg[b'args'][1].decode('latin1'))
|
||||||
else:
|
else:
|
||||||
sess.run_repl()
|
sess.run_repl()
|
||||||
return sess
|
return sess
|
||||||
|
@ -51,10 +51,10 @@ class CCApplication(web.Application):
|
||||||
if sess is not None:
|
if sess is not None:
|
||||||
async for msg in self._bin_messages(ws):
|
async for msg in self._bin_messages(ws):
|
||||||
msg = ser.deserialize(msg)
|
msg = ser.deserialize(msg)
|
||||||
if msg['action'] == 'event':
|
if msg[b'action'] == b'event':
|
||||||
sess.on_event(msg['event'], msg['params'])
|
sess.on_event(msg[b'event'].decode('latin1'), msg[b'params'])
|
||||||
elif msg['action'] == 'task_result':
|
elif msg[b'action'] == b'task_result':
|
||||||
sess.on_task_result(msg['task_id'], msg['result'])
|
sess.on_task_result(msg[b'task_id'].decode('latin1'), msg[b'result'])
|
||||||
else:
|
else:
|
||||||
await ws.send_bytes(ser.serialize({
|
await ws.send_bytes(ser.serialize({
|
||||||
'action': 'close',
|
'action': 'close',
|
||||||
|
|
|
@ -73,22 +73,22 @@ class StdFileProxy:
|
||||||
raise RuntimeError(
|
raise RuntimeError(
|
||||||
"Computercraft environment doesn't support "
|
"Computercraft environment doesn't support "
|
||||||
"stdin readline method with parameter")
|
"stdin readline method with parameter")
|
||||||
return rproc.string(eval_lua(
|
return eval_lua(
|
||||||
return_lua_call('io.read')
|
return_lua_call('io.read')
|
||||||
)) + '\n'
|
).take_string() + '\n'
|
||||||
|
|
||||||
def write(self, s):
|
def write(self, s):
|
||||||
if _is_global_greenlet():
|
if _is_global_greenlet():
|
||||||
return self._native.write(s)
|
return self._native.write(s)
|
||||||
else:
|
else:
|
||||||
if self._err:
|
if self._err:
|
||||||
return rproc.nil(eval_lua(
|
return eval_lua(
|
||||||
lua_call('io.stderr:write', s)
|
lua_call('io.stderr:write', s)
|
||||||
))
|
).take_none()
|
||||||
else:
|
else:
|
||||||
return rproc.nil(eval_lua(
|
return eval_lua(
|
||||||
lua_call('io.write', s)
|
lua_call('io.write', s)
|
||||||
))
|
).take_none()
|
||||||
|
|
||||||
def fileno(self):
|
def fileno(self):
|
||||||
if _is_global_greenlet():
|
if _is_global_greenlet():
|
||||||
|
@ -147,9 +147,10 @@ def eval_lua(lua_code, immediate=False):
|
||||||
})
|
})
|
||||||
result = get_current_session()._server_greenlet.switch(request)
|
result = get_current_session()._server_greenlet.switch(request)
|
||||||
# debug('{} → {}'.format(lua_code, repr(result)))
|
# debug('{} → {}'.format(lua_code, repr(result)))
|
||||||
|
rp = rproc.ResultProc(result)
|
||||||
if not immediate:
|
if not immediate:
|
||||||
result = rproc.coro(result)
|
rp.check_bool_error()
|
||||||
return result
|
return rp
|
||||||
|
|
||||||
|
|
||||||
@contextmanager
|
@contextmanager
|
||||||
|
@ -342,7 +343,7 @@ class CCSession:
|
||||||
|
|
||||||
def run_program(self, program):
|
def run_program(self, program):
|
||||||
def _run_program():
|
def _run_program():
|
||||||
p, code = eval_lua('''
|
rp = eval_lua('''
|
||||||
local p = fs.combine(shell.dir(), {})
|
local p = fs.combine(shell.dir(), {})
|
||||||
if not fs.exists(p) then return nil end
|
if not fs.exists(p) then return nil end
|
||||||
if fs.isDir(p) then return nil end
|
if fs.isDir(p) then return nil end
|
||||||
|
@ -351,6 +352,8 @@ local code = f.readAll()
|
||||||
f.close()
|
f.close()
|
||||||
return p, code
|
return p, code
|
||||||
'''.lstrip().format(lua_string(program)))
|
'''.lstrip().format(lua_string(program)))
|
||||||
|
p = rp.take_string()
|
||||||
|
code = rp.take_string()
|
||||||
cc = compile(code, p, 'exec')
|
cc = compile(code, p, 'exec')
|
||||||
exec(cc, {'__file__': p})
|
exec(cc, {'__file__': p})
|
||||||
|
|
||||||
|
|
|
@ -2,7 +2,6 @@ from types import ModuleType
|
||||||
|
|
||||||
from ..errors import LuaException
|
from ..errors import LuaException
|
||||||
from ..lua import lua_string
|
from ..lua import lua_string
|
||||||
from ..rproc import boolean, option_string
|
|
||||||
from ..sess import eval_lua
|
from ..sess import eval_lua
|
||||||
|
|
||||||
|
|
||||||
|
@ -26,7 +25,7 @@ def import_file(path: str, relative_to: str = None):
|
||||||
lua_string(relative_to),
|
lua_string(relative_to),
|
||||||
path_expr,
|
path_expr,
|
||||||
)
|
)
|
||||||
source = option_string(eval_lua('''
|
source = eval_lua('''
|
||||||
local p = {}
|
local p = {}
|
||||||
if not fs.exists(p) then return nil end
|
if not fs.exists(p) then return nil end
|
||||||
if fs.isDir(p) then return nil end
|
if fs.isDir(p) then return nil end
|
||||||
|
@ -36,7 +35,7 @@ f.close()
|
||||||
return src
|
return src
|
||||||
'''.lstrip().format(
|
'''.lstrip().format(
|
||||||
path_expr,
|
path_expr,
|
||||||
)))
|
)).take_option_string()
|
||||||
if source is None:
|
if source is None:
|
||||||
raise ImportError('File not found: {}'.format(path))
|
raise ImportError('File not found: {}'.format(path))
|
||||||
cc = compile(source, mod.__name__, 'exec')
|
cc = compile(source, mod.__name__, 'exec')
|
||||||
|
@ -45,16 +44,16 @@ return src
|
||||||
|
|
||||||
|
|
||||||
def is_commands() -> bool:
|
def is_commands() -> bool:
|
||||||
return boolean(eval_lua('return commands ~= nil'))
|
return eval_lua('return commands ~= nil').take_bool()
|
||||||
|
|
||||||
|
|
||||||
def is_multishell() -> bool:
|
def is_multishell() -> bool:
|
||||||
return boolean(eval_lua('return multishell ~= nil'))
|
return eval_lua('return multishell ~= nil').take_bool()
|
||||||
|
|
||||||
|
|
||||||
def is_turtle() -> bool:
|
def is_turtle() -> bool:
|
||||||
return boolean(eval_lua('return turtle ~= nil'))
|
return eval_lua('return turtle ~= nil').take_bool()
|
||||||
|
|
||||||
|
|
||||||
def is_pocket() -> bool:
|
def is_pocket() -> bool:
|
||||||
return boolean(eval_lua('return pocket ~= nil'))
|
return eval_lua('return pocket ~= nil').take_bool()
|
||||||
|
|
|
@ -1,6 +1,5 @@
|
||||||
from typing import Tuple
|
from typing import Tuple
|
||||||
|
|
||||||
from ..rproc import boolean, integer, tuple3_number
|
|
||||||
from ..sess import eval_lua_method_factory
|
from ..sess import eval_lua_method_factory
|
||||||
|
|
||||||
|
|
||||||
|
@ -55,23 +54,24 @@ black = 0x8000
|
||||||
# combine, subtract and test are mostly for redstone.setBundledOutput
|
# combine, subtract and test are mostly for redstone.setBundledOutput
|
||||||
|
|
||||||
def combine(*colors: int) -> int:
|
def combine(*colors: int) -> int:
|
||||||
return integer(method('combine', *colors))
|
return method('combine', *colors).take_int()
|
||||||
|
|
||||||
|
|
||||||
def subtract(color_set: int, *colors: int) -> int:
|
def subtract(color_set: int, *colors: int) -> int:
|
||||||
return integer(method('subtract', color_set, *colors))
|
return method('subtract', color_set, *colors).take_int()
|
||||||
|
|
||||||
|
|
||||||
def test(colors: int, color: int) -> bool:
|
def test(colors: int, color: int) -> bool:
|
||||||
return boolean(method('test', colors, color))
|
return method('test', colors, color).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def packRGB(r: float, g: float, b: float) -> int:
|
def packRGB(r: float, g: float, b: float) -> int:
|
||||||
return integer(method('packRGB', r, g, b))
|
return method('packRGB', r, g, b).take_int()
|
||||||
|
|
||||||
|
|
||||||
def unpackRGB(rgb: int) -> Tuple[float, float, float]:
|
def unpackRGB(rgb: int) -> Tuple[float, float, float]:
|
||||||
return tuple3_number(method('unpackRGB', rgb))
|
rp = method('unpackRGB', rgb)
|
||||||
|
return tuple(rp.take_number() for _ in range(3))
|
||||||
|
|
||||||
|
|
||||||
# use these chars for term.blit
|
# use these chars for term.blit
|
||||||
|
|
|
@ -1,10 +1,8 @@
|
||||||
from typing import Tuple, List, Optional
|
from typing import Tuple, List, Optional
|
||||||
|
|
||||||
from ..rproc import tuple3_integer, any_dict, any_list, array_string, fact_tuple, boolean, option_integer
|
|
||||||
from ..sess import eval_lua_method_factory
|
from ..sess import eval_lua_method_factory
|
||||||
|
|
||||||
|
|
||||||
command_result = fact_tuple(boolean, array_string, option_integer, tail_nils=1)
|
|
||||||
method = eval_lua_method_factory('commands.')
|
method = eval_lua_method_factory('commands.')
|
||||||
|
|
||||||
|
|
||||||
|
@ -18,20 +16,25 @@ __all__ = (
|
||||||
|
|
||||||
|
|
||||||
def exec(command: str) -> Tuple[bool, List[str], Optional[int]]:
|
def exec(command: str) -> Tuple[bool, List[str], Optional[int]]:
|
||||||
return command_result(method('exec', command))
|
rp = method('exec', command)
|
||||||
|
success = rp.take_bool()
|
||||||
|
log = rp.take_list_of_strings()
|
||||||
|
n = rp.take_option_int()
|
||||||
|
return success, log, n
|
||||||
|
|
||||||
|
|
||||||
def list() -> List[str]:
|
def list() -> List[str]:
|
||||||
return array_string(method('list'))
|
return method('list').take_list_of_strings()
|
||||||
|
|
||||||
|
|
||||||
def getBlockPosition() -> Tuple[int, int, int]:
|
def getBlockPosition() -> Tuple[int, int, int]:
|
||||||
return tuple3_integer(method('getBlockPosition'))
|
rp = method('getBlockPosition')
|
||||||
|
return tuple(rp.take_int() for _ in range(3))
|
||||||
|
|
||||||
|
|
||||||
def getBlockInfo(x: int, y: int, z: int) -> dict:
|
def getBlockInfo(x: int, y: int, z: int) -> dict:
|
||||||
return any_dict(method('getBlockInfo', x, y, z))
|
return method('getBlockInfo', x, y, z).take_dict()
|
||||||
|
|
||||||
|
|
||||||
def getBlockInfos(x1: int, y1: int, z1: int, x2: int, y2: int, z2: int) -> List[dict]:
|
def getBlockInfos(x1: int, y1: int, z1: int, x2: int, y2: int, z2: int) -> List[dict]:
|
||||||
return any_list(method('getBlockInfos', x1, y1, z1, x2, y2, z2))
|
return method('getBlockInfos', x1, y1, z1, x2, y2, z2).take_list()
|
||||||
|
|
|
@ -1,6 +1,5 @@
|
||||||
from typing import Optional, Union
|
from typing import Optional, Union
|
||||||
|
|
||||||
from ..rproc import boolean, nil, option_integer, option_string, option_string_bool
|
|
||||||
from ..sess import eval_lua_method_factory
|
from ..sess import eval_lua_method_factory
|
||||||
|
|
||||||
|
|
||||||
|
@ -23,44 +22,44 @@ __all__ = (
|
||||||
|
|
||||||
|
|
||||||
def isPresent(side: str) -> bool:
|
def isPresent(side: str) -> bool:
|
||||||
return boolean(method('isPresent', side))
|
return method('isPresent', side).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def hasData(side: str) -> bool:
|
def hasData(side: str) -> bool:
|
||||||
return boolean(method('hasData', side))
|
return method('hasData', side).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def getMountPath(side: str) -> Optional[str]:
|
def getMountPath(side: str) -> Optional[str]:
|
||||||
return option_string(method('getMountPath', side))
|
return method('getMountPath', side).take_option_string()
|
||||||
|
|
||||||
|
|
||||||
def setLabel(side: str, label: str):
|
def setLabel(side: str, label: str):
|
||||||
return nil(method('setLabel', side, label))
|
return method('setLabel', side, label).take_none()
|
||||||
|
|
||||||
|
|
||||||
def getLabel(side: str) -> Optional[str]:
|
def getLabel(side: str) -> Optional[str]:
|
||||||
return option_string(method('getLabel', side))
|
return method('getLabel', side).take_option_string()
|
||||||
|
|
||||||
|
|
||||||
def getID(side: str) -> Optional[int]:
|
def getID(side: str) -> Optional[int]:
|
||||||
return option_integer(method('getID', side))
|
return method('getID', side).take_option_int()
|
||||||
|
|
||||||
|
|
||||||
def hasAudio(side: str) -> bool:
|
def hasAudio(side: str) -> bool:
|
||||||
return boolean(method('hasAudio', side))
|
return method('hasAudio', side).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def getAudioTitle(side: str) -> Optional[Union[bool, str]]:
|
def getAudioTitle(side: str) -> Optional[Union[bool, str]]:
|
||||||
return option_string_bool(method('getAudioTitle', side))
|
return method('getAudioTitle', side).take_option_string_bool()
|
||||||
|
|
||||||
|
|
||||||
def playAudio(side: str):
|
def playAudio(side: str):
|
||||||
return nil(method('playAudio', side))
|
return method('playAudio', side).take_none()
|
||||||
|
|
||||||
|
|
||||||
def stopAudio(side: str):
|
def stopAudio(side: str):
|
||||||
return nil(method('stopAudio', side))
|
return method('stopAudio', side).take_none()
|
||||||
|
|
||||||
|
|
||||||
def eject(side: str):
|
def eject(side: str):
|
||||||
return nil(method('eject', side))
|
return method('eject', side).take_none()
|
||||||
|
|
|
@ -1,55 +1,31 @@
|
||||||
import builtins
|
|
||||||
from contextlib import contextmanager
|
from contextlib import contextmanager
|
||||||
from typing import Optional, List
|
from typing import Optional, List
|
||||||
|
|
||||||
from .base import BaseSubAPI
|
from .base import BaseSubAPI
|
||||||
from ..errors import LuaException
|
from ..lua import lua_call
|
||||||
from ..lua import lua_call, lua_args, lua_string
|
from ..sess import eval_lua_method_factory, lua_context_object
|
||||||
from ..rproc import boolean, string, integer, nil, array_string, option_string, fact_scheme_dict
|
|
||||||
from ..sess import eval_lua, eval_lua_method_factory, lua_context_object
|
|
||||||
|
|
||||||
|
|
||||||
attribute = fact_scheme_dict({
|
|
||||||
'created': integer,
|
|
||||||
'modification': integer,
|
|
||||||
'isDir': boolean,
|
|
||||||
'size': integer,
|
|
||||||
}, {})
|
|
||||||
|
|
||||||
|
|
||||||
class SeekMixin:
|
class SeekMixin:
|
||||||
def seek(self, whence: str = None, offset: int = None) -> int:
|
def seek(self, whence: str = None, offset: int = None) -> int:
|
||||||
# whence: set, cur, end
|
# whence: set, cur, end
|
||||||
r = self._method('seek', whence, offset)
|
rp = self._method('seek', whence, offset)
|
||||||
if isinstance(r, builtins.list):
|
rp.check_nil_error()
|
||||||
assert r[0] is False
|
return rp.take_int()
|
||||||
raise LuaException(r[1])
|
|
||||||
return integer(r)
|
|
||||||
|
|
||||||
|
|
||||||
class ReadHandle(BaseSubAPI):
|
class ReadMixin:
|
||||||
def _decode(self, b):
|
def _take(self, rp):
|
||||||
return b.decode('utf-8')
|
raise NotImplementedError
|
||||||
|
|
||||||
def _read(self, name, params, val):
|
|
||||||
code = '''
|
|
||||||
local s = {}.{}({})
|
|
||||||
if s == nil then return nil end
|
|
||||||
s = s:gsub('.', function(c) return string.format('%02X', string.byte(c)) end)
|
|
||||||
return s
|
|
||||||
'''.lstrip().format(
|
|
||||||
self.get_expr_code(), name, lua_args(*params),
|
|
||||||
)
|
|
||||||
return self._decode(bytes.fromhex(val(eval_lua(code))))
|
|
||||||
|
|
||||||
def read(self, count: int = 1) -> Optional[str]:
|
def read(self, count: int = 1) -> Optional[str]:
|
||||||
return self._read('read', (count, ), option_string)
|
return self._take(self._method('read', count))
|
||||||
|
|
||||||
def readLine(self) -> Optional[str]:
|
def readLine(self, withTrailing: bool = False) -> Optional[str]:
|
||||||
return self._read('readLine', (), option_string)
|
return self._take(self._method('readLine', withTrailing))
|
||||||
|
|
||||||
def readAll(self) -> str:
|
def readAll(self) -> Optional[str]:
|
||||||
return self._read('readAll', (), string)
|
return self._take(self._method('readAll'))
|
||||||
|
|
||||||
def __iter__(self):
|
def __iter__(self):
|
||||||
return self
|
return self
|
||||||
|
@ -61,39 +37,38 @@ return s
|
||||||
return line
|
return line
|
||||||
|
|
||||||
|
|
||||||
class BinaryReadHandle(ReadHandle, SeekMixin):
|
class WriteMixin:
|
||||||
def _decode(self, b):
|
def _put(self, t):
|
||||||
return b
|
raise NotImplementedError
|
||||||
|
|
||||||
|
|
||||||
class WriteHandle(BaseSubAPI):
|
|
||||||
def _encode(self, s):
|
|
||||||
return s.encode('utf-8')
|
|
||||||
|
|
||||||
def _write(self, name, text, val):
|
|
||||||
code = '''
|
|
||||||
local s = {}
|
|
||||||
s = s:gsub('..', function(cc) return string.char(tonumber(cc, 16)) end)
|
|
||||||
return {}.{}(s)
|
|
||||||
'''.lstrip().format(
|
|
||||||
lua_string(self._encode(text).hex()),
|
|
||||||
self.get_expr_code(), name,
|
|
||||||
)
|
|
||||||
return val(eval_lua(code))
|
|
||||||
|
|
||||||
def write(self, text: str):
|
def write(self, text: str):
|
||||||
return nil(self._method('write', text))
|
return self._method('write', self._put(text)).take_none()
|
||||||
|
|
||||||
def writeLine(self, text: str):
|
|
||||||
return nil(self._method('writeLine', text))
|
|
||||||
|
|
||||||
def flush(self):
|
def flush(self):
|
||||||
return nil(self._method('flush'))
|
return self._method('flush').take_none()
|
||||||
|
|
||||||
|
|
||||||
class BinaryWriteHandle(WriteHandle, SeekMixin):
|
class ReadHandle(ReadMixin, BaseSubAPI):
|
||||||
def _encode(self, s):
|
def _take(self, rp):
|
||||||
return s
|
return rp.take_option_unicode()
|
||||||
|
|
||||||
|
|
||||||
|
class BinaryReadHandle(ReadMixin, SeekMixin, BaseSubAPI):
|
||||||
|
def _take(self, rp):
|
||||||
|
return rp.take_option_bytes()
|
||||||
|
|
||||||
|
|
||||||
|
class WriteHandle(WriteMixin, BaseSubAPI):
|
||||||
|
def _put(self, t: str) -> bytes:
|
||||||
|
return t.encode('utf-8')
|
||||||
|
|
||||||
|
def writeLine(self, text: str):
|
||||||
|
return self.write(text + '\n')
|
||||||
|
|
||||||
|
|
||||||
|
class BinaryWriteHandle(WriteMixin, SeekMixin, BaseSubAPI):
|
||||||
|
def _put(self, b: bytes) -> bytes:
|
||||||
|
return b
|
||||||
|
|
||||||
|
|
||||||
method = eval_lua_method_factory('fs.')
|
method = eval_lua_method_factory('fs.')
|
||||||
|
@ -124,55 +99,55 @@ __all__ = (
|
||||||
|
|
||||||
|
|
||||||
def list(path: str) -> List[str]:
|
def list(path: str) -> List[str]:
|
||||||
return array_string(method('list', path))
|
return method('list', path).take_list_of_strings()
|
||||||
|
|
||||||
|
|
||||||
def exists(path: str) -> bool:
|
def exists(path: str) -> bool:
|
||||||
return boolean(method('exists', path))
|
return method('exists', path).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def isDir(path: str) -> bool:
|
def isDir(path: str) -> bool:
|
||||||
return boolean(method('isDir', path))
|
return method('isDir', path).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def isReadOnly(path: str) -> bool:
|
def isReadOnly(path: str) -> bool:
|
||||||
return boolean(method('isReadOnly', path))
|
return method('isReadOnly', path).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def getDrive(path: str) -> Optional[str]:
|
def getDrive(path: str) -> Optional[str]:
|
||||||
return option_string(method('getDrive', path))
|
return method('getDrive', path).take_option_string()
|
||||||
|
|
||||||
|
|
||||||
def getSize(path: str) -> int:
|
def getSize(path: str) -> int:
|
||||||
return integer(method('getSize', path))
|
return method('getSize', path).take_int()
|
||||||
|
|
||||||
|
|
||||||
def getFreeSpace(path: str) -> int:
|
def getFreeSpace(path: str) -> int:
|
||||||
return integer(method('getFreeSpace', path))
|
return method('getFreeSpace', path).take_int()
|
||||||
|
|
||||||
|
|
||||||
def getCapacity(path: str) -> int:
|
def getCapacity(path: str) -> int:
|
||||||
return integer(method('getCapacity', path))
|
return method('getCapacity', path).take_int()
|
||||||
|
|
||||||
|
|
||||||
def makeDir(path: str):
|
def makeDir(path: str):
|
||||||
return nil(method('makeDir', path))
|
return method('makeDir', path).take_none()
|
||||||
|
|
||||||
|
|
||||||
def move(fromPath: str, toPath: str):
|
def move(fromPath: str, toPath: str):
|
||||||
return nil(method('move', fromPath, toPath))
|
return method('move', fromPath, toPath).take_none()
|
||||||
|
|
||||||
|
|
||||||
def copy(fromPath: str, toPath: str):
|
def copy(fromPath: str, toPath: str):
|
||||||
return nil(method('copy', fromPath, toPath))
|
return method('copy', fromPath, toPath).take_none()
|
||||||
|
|
||||||
|
|
||||||
def delete(path: str):
|
def delete(path: str):
|
||||||
return nil(method('delete', path))
|
return method('delete', path).take_none()
|
||||||
|
|
||||||
|
|
||||||
def combine(basePath: str, localPath: str) -> str:
|
def combine(basePath: str, localPath: str) -> str:
|
||||||
return string(method('combine', basePath, localPath))
|
return method('combine', basePath, localPath).take_string()
|
||||||
|
|
||||||
|
|
||||||
@contextmanager
|
@contextmanager
|
||||||
|
@ -199,27 +174,39 @@ def open(path: str, mode: str):
|
||||||
|
|
||||||
|
|
||||||
def find(wildcard: str) -> List[str]:
|
def find(wildcard: str) -> List[str]:
|
||||||
return array_string(method('find', wildcard))
|
return method('find', wildcard).take_list_of_strings()
|
||||||
|
|
||||||
|
|
||||||
def getDir(path: str) -> str:
|
def getDir(path: str) -> str:
|
||||||
return string(method('getDir', path))
|
return method('getDir', path).take_string()
|
||||||
|
|
||||||
|
|
||||||
def getName(path: str) -> str:
|
def getName(path: str) -> str:
|
||||||
return string(method('getName', path))
|
return method('getName', path).take_string()
|
||||||
|
|
||||||
|
|
||||||
def isDriveRoot(path: str) -> bool:
|
def isDriveRoot(path: str) -> bool:
|
||||||
return boolean(method('isDriveRoot', path))
|
return method('isDriveRoot', path).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def complete(
|
def complete(
|
||||||
partialName: str, path: str, includeFiles: bool = None, includeDirs: bool = None,
|
partialName: str, path: str, includeFiles: bool = None, includeDirs: bool = None,
|
||||||
) -> List[str]:
|
) -> List[str]:
|
||||||
return array_string(method(
|
return method(
|
||||||
'complete', partialName, path, includeFiles, includeDirs))
|
'complete', partialName, path, includeFiles, includeDirs,
|
||||||
|
).take_list_of_strings()
|
||||||
|
|
||||||
|
|
||||||
def attributes(path: str) -> dict:
|
def attributes(path: str) -> dict:
|
||||||
return attribute(method('attributes', path))
|
tp = method('attributes', path).take_dict((
|
||||||
|
b'created',
|
||||||
|
b'modification',
|
||||||
|
b'isDir',
|
||||||
|
b'size',
|
||||||
|
))
|
||||||
|
r = {}
|
||||||
|
r['created'] = tp.take_int()
|
||||||
|
r['modification'] = tp.take_int()
|
||||||
|
r['isDir'] = tp.take_bool()
|
||||||
|
r['size'] = tp.take_int()
|
||||||
|
return r
|
||||||
|
|
|
@ -19,4 +19,7 @@ CHANNEL_GPS = 65534
|
||||||
|
|
||||||
|
|
||||||
def locate(timeout: LuaNum = None, debug: bool = None) -> Optional[Tuple[LuaNum, LuaNum, LuaNum]]:
|
def locate(timeout: LuaNum = None, debug: bool = None) -> Optional[Tuple[LuaNum, LuaNum, LuaNum]]:
|
||||||
return option_tuple3_number(method('locate', timeout, debug))
|
rp = method('locate', timeout, debug)
|
||||||
|
if rp.peek() is None:
|
||||||
|
return None
|
||||||
|
return tuple(rp.take_number() for _ in range(3))
|
||||||
|
|
|
@ -1,6 +1,5 @@
|
||||||
from typing import Optional, List
|
from typing import Optional, List
|
||||||
|
|
||||||
from ..rproc import string, nil, array_string, option_string
|
|
||||||
from ..sess import eval_lua_method_factory
|
from ..sess import eval_lua_method_factory
|
||||||
|
|
||||||
|
|
||||||
|
@ -17,20 +16,20 @@ __all__ = (
|
||||||
|
|
||||||
|
|
||||||
def path() -> str:
|
def path() -> str:
|
||||||
return string(method('path'))
|
return method('path').take_string()
|
||||||
|
|
||||||
|
|
||||||
def setPath(path: str):
|
def setPath(path: str):
|
||||||
return nil(method('setPath', path))
|
return method('setPath', path).take_none()
|
||||||
|
|
||||||
|
|
||||||
def lookup(topic: str) -> Optional[str]:
|
def lookup(topic: str) -> Optional[str]:
|
||||||
return option_string(method('lookup', topic))
|
return method('lookup', topic).take_option_string()
|
||||||
|
|
||||||
|
|
||||||
def topics() -> List[str]:
|
def topics() -> List[str]:
|
||||||
return array_string(method('topics'))
|
return method('topics').take_list_of_strings()
|
||||||
|
|
||||||
|
|
||||||
def completeTopic(topicPrefix: str) -> List[str]:
|
def completeTopic(topicPrefix: str) -> List[str]:
|
||||||
return array_string(method('completeTopic', topicPrefix))
|
return method('completeTopic', topicPrefix).take_list_of_strings()
|
||||||
|
|
|
@ -1,7 +1,6 @@
|
||||||
from typing import Optional
|
from typing import Optional
|
||||||
|
|
||||||
from ..lua import lua_string
|
from ..lua import lua_string
|
||||||
from ..rproc import option_integer, option_string
|
|
||||||
from ..sess import eval_lua, eval_lua_method_factory
|
from ..sess import eval_lua, eval_lua_method_factory
|
||||||
|
|
||||||
|
|
||||||
|
@ -17,12 +16,12 @@ __all__ = (
|
||||||
def getCode(name: str) -> Optional[int]:
|
def getCode(name: str) -> Optional[int]:
|
||||||
# replaces properties
|
# replaces properties
|
||||||
# keys.space → keys.getCode('space')
|
# keys.space → keys.getCode('space')
|
||||||
return option_integer(eval_lua('''
|
return eval_lua('''
|
||||||
if type(keys[{key}]) == 'number' then
|
if type(keys[{key}]) == 'number' then
|
||||||
return keys[{key}]
|
return keys[{key}]
|
||||||
end
|
end
|
||||||
return nil'''.format(key=lua_string(name))))
|
return nil'''.format(key=lua_string(name))).take_option_int()
|
||||||
|
|
||||||
|
|
||||||
def getName(code: int) -> Optional[str]:
|
def getName(code: int) -> Optional[str]:
|
||||||
return option_string(method('getName', code))
|
return method('getName', code).take_option_string()
|
||||||
|
|
|
@ -1,60 +1,62 @@
|
||||||
from typing import Tuple
|
from typing import Tuple
|
||||||
|
|
||||||
from ..lua import LuaExpr
|
from ..lua import LuaExpr
|
||||||
from ..rproc import boolean, nil, integer, tuple3_number, tuple2_integer
|
|
||||||
|
|
||||||
|
|
||||||
class TermMixin:
|
class TermMixin:
|
||||||
def write(self, text: str):
|
def write(self, text: str):
|
||||||
return nil(self._method('write', text))
|
return self._method('write', text).take_none()
|
||||||
|
|
||||||
def blit(self, text: str, textColors: str, backgroundColors: str):
|
def blit(self, text: str, textColors: str, backgroundColors: str):
|
||||||
return nil(self._method('blit', text, textColors, backgroundColors))
|
return self._method('blit', text, textColors, backgroundColors).take_none()
|
||||||
|
|
||||||
def clear(self):
|
def clear(self):
|
||||||
return nil(self._method('clear'))
|
return self._method('clear').take_none()
|
||||||
|
|
||||||
def clearLine(self):
|
def clearLine(self):
|
||||||
return nil(self._method('clearLine'))
|
return self._method('clearLine').take_none()
|
||||||
|
|
||||||
def getCursorPos(self) -> Tuple[int, int]:
|
def getCursorPos(self) -> Tuple[int, int]:
|
||||||
return tuple2_integer(self._method('getCursorPos'))
|
rp = self._method('getCursorPos')
|
||||||
|
return tuple(rp.take_int() for _ in range(2))
|
||||||
|
|
||||||
def setCursorPos(self, x: int, y: int):
|
def setCursorPos(self, x: int, y: int):
|
||||||
return nil(self._method('setCursorPos', x, y))
|
return self._method('setCursorPos', x, y).take_none()
|
||||||
|
|
||||||
def getCursorBlink(self) -> bool:
|
def getCursorBlink(self) -> bool:
|
||||||
return boolean(self._method('getCursorBlink'))
|
return self._method('getCursorBlink').take_bool()
|
||||||
|
|
||||||
def setCursorBlink(self, value: bool):
|
def setCursorBlink(self, value: bool):
|
||||||
return nil(self._method('setCursorBlink', value))
|
return self._method('setCursorBlink', value).take_none()
|
||||||
|
|
||||||
def isColor(self) -> bool:
|
def isColor(self) -> bool:
|
||||||
return boolean(self._method('isColor'))
|
return self._method('isColor').take_bool()
|
||||||
|
|
||||||
def getSize(self) -> Tuple[int, int]:
|
def getSize(self) -> Tuple[int, int]:
|
||||||
return tuple2_integer(self._method('getSize'))
|
rp = self._method('getSize')
|
||||||
|
return tuple(rp.take_int() for _ in range(2))
|
||||||
|
|
||||||
def scroll(self, lines: int):
|
def scroll(self, lines: int):
|
||||||
return nil(self._method('scroll', lines))
|
return self._method('scroll', lines).take_none()
|
||||||
|
|
||||||
def setTextColor(self, colorID: int):
|
def setTextColor(self, colorID: int):
|
||||||
return nil(self._method('setTextColor', colorID))
|
return self._method('setTextColor', colorID).take_none()
|
||||||
|
|
||||||
def getTextColor(self) -> int:
|
def getTextColor(self) -> int:
|
||||||
return integer(self._method('getTextColor'))
|
return self._method('getTextColor').take_int()
|
||||||
|
|
||||||
def setBackgroundColor(self, colorID: int):
|
def setBackgroundColor(self, colorID: int):
|
||||||
return nil(self._method('setBackgroundColor', colorID))
|
return self._method('setBackgroundColor', colorID).take_none()
|
||||||
|
|
||||||
def getBackgroundColor(self) -> int:
|
def getBackgroundColor(self) -> int:
|
||||||
return integer(self._method('getBackgroundColor'))
|
return self._method('getBackgroundColor').take_int()
|
||||||
|
|
||||||
def getPaletteColor(self, colorID: int) -> Tuple[float, float, float]:
|
def getPaletteColor(self, colorID: int) -> Tuple[float, float, float]:
|
||||||
return tuple3_number(self._method('getPaletteColor', colorID))
|
rp = self._method('getPaletteColor', colorID)
|
||||||
|
return tuple(rp.take_number() for _ in range(3))
|
||||||
|
|
||||||
def setPaletteColor(self, colorID: int, r: float, g: float, b: float):
|
def setPaletteColor(self, colorID: int, r: float, g: float, b: float):
|
||||||
return nil(self._method('setPaletteColor', colorID, r, g, b))
|
return self._method('setPaletteColor', colorID, r, g, b).take_none()
|
||||||
|
|
||||||
|
|
||||||
class TermTarget(LuaExpr):
|
class TermTarget(LuaExpr):
|
||||||
|
|
|
@ -1,6 +1,5 @@
|
||||||
from typing import Optional
|
from typing import Optional
|
||||||
|
|
||||||
from ..rproc import integer, nil, boolean, option_string
|
|
||||||
from ..sess import eval_lua_method_factory
|
from ..sess import eval_lua_method_factory
|
||||||
|
|
||||||
|
|
||||||
|
@ -19,28 +18,28 @@ __all__ = (
|
||||||
|
|
||||||
|
|
||||||
def getCurrent() -> int:
|
def getCurrent() -> int:
|
||||||
return integer(method('getCurrent'))
|
return method('getCurrent').take_int()
|
||||||
|
|
||||||
|
|
||||||
def getCount() -> int:
|
def getCount() -> int:
|
||||||
return integer(method('getCount'))
|
return method('getCount').take_int()
|
||||||
|
|
||||||
|
|
||||||
def launch(environment: dict, programPath: str, *args: str) -> int:
|
def launch(environment: dict, programPath: str, *args: str) -> int:
|
||||||
return integer(method('launch', environment, programPath, *args))
|
return method('launch', environment, programPath, *args).take_int()
|
||||||
|
|
||||||
|
|
||||||
def setTitle(tabID: int, title: str):
|
def setTitle(tabID: int, title: str):
|
||||||
return nil(method('setTitle', tabID, title))
|
return method('setTitle', tabID, title).take_none()
|
||||||
|
|
||||||
|
|
||||||
def getTitle(tabID: int) -> Optional[str]:
|
def getTitle(tabID: int) -> Optional[str]:
|
||||||
return option_string(method('getTitle', tabID))
|
return method('getTitle', tabID).take_option_string()
|
||||||
|
|
||||||
|
|
||||||
def setFocus(tabID: int) -> bool:
|
def setFocus(tabID: int) -> bool:
|
||||||
return boolean(method('setFocus', tabID))
|
return method('setFocus', tabID).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def getFocus() -> int:
|
def getFocus() -> int:
|
||||||
return integer(method('getFocus'))
|
return method('getFocus').take_int()
|
||||||
|
|
|
@ -1,7 +1,6 @@
|
||||||
from typing import Optional, List
|
from typing import Optional, List
|
||||||
|
|
||||||
from ..lua import LuaNum
|
from ..lua import LuaNum
|
||||||
from ..rproc import nil, string, option_string, number, integer, boolean
|
|
||||||
from ..sess import eval_lua_method_factory, get_current_greenlet
|
from ..sess import eval_lua_method_factory, get_current_greenlet
|
||||||
|
|
||||||
|
|
||||||
|
@ -31,23 +30,23 @@ __all__ = (
|
||||||
|
|
||||||
|
|
||||||
def version() -> str:
|
def version() -> str:
|
||||||
return string(method('version'))
|
return method('version').take_string()
|
||||||
|
|
||||||
|
|
||||||
def getComputerID() -> int:
|
def getComputerID() -> int:
|
||||||
return integer(method('getComputerID'))
|
return method('getComputerID').take_int()
|
||||||
|
|
||||||
|
|
||||||
def getComputerLabel() -> Optional[str]:
|
def getComputerLabel() -> Optional[str]:
|
||||||
return option_string(method('getComputerLabel'))
|
return method('getComputerLabel').take_option_string()
|
||||||
|
|
||||||
|
|
||||||
def setComputerLabel(label: Optional[str]):
|
def setComputerLabel(label: Optional[str]):
|
||||||
return nil(method('setComputerLabel', label))
|
return method('setComputerLabel', label).take_none()
|
||||||
|
|
||||||
|
|
||||||
def run(environment: dict, programPath: str, *args: List[str]):
|
def run(environment: dict, programPath: str, *args: List[str]):
|
||||||
return boolean(method('run', environment, programPath, *args))
|
return method('run', environment, programPath, *args).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def captureEvent(event: str):
|
def captureEvent(event: str):
|
||||||
|
@ -68,12 +67,12 @@ def captureEvent(event: str):
|
||||||
|
|
||||||
|
|
||||||
def queueEvent(event: str, *params):
|
def queueEvent(event: str, *params):
|
||||||
return nil(method('queueEvent', event, *params))
|
return method('queueEvent', event, *params).take_none()
|
||||||
|
|
||||||
|
|
||||||
def clock() -> LuaNum:
|
def clock() -> LuaNum:
|
||||||
# number of game ticks * 0.05, roughly seconds
|
# number of game ticks * 0.05, roughly seconds
|
||||||
return number(method('clock'))
|
return method('clock').take_number()
|
||||||
|
|
||||||
|
|
||||||
# regarding ingame parameter below:
|
# regarding ingame parameter below:
|
||||||
|
@ -82,42 +81,42 @@ def clock() -> LuaNum:
|
||||||
|
|
||||||
def time() -> LuaNum:
|
def time() -> LuaNum:
|
||||||
# in hours 0..24
|
# in hours 0..24
|
||||||
return number(method('time', 'ingame'))
|
return method('time', 'ingame').take_number()
|
||||||
|
|
||||||
|
|
||||||
def day() -> int:
|
def day() -> int:
|
||||||
return integer(method('day', 'ingame'))
|
return method('day', 'ingame').take_int()
|
||||||
|
|
||||||
|
|
||||||
def epoch() -> int:
|
def epoch() -> int:
|
||||||
return integer(method('epoch', 'ingame'))
|
return method('epoch', 'ingame').take_int()
|
||||||
|
|
||||||
|
|
||||||
def sleep(seconds: LuaNum):
|
def sleep(seconds: LuaNum):
|
||||||
return nil(method('sleep', seconds))
|
return method('sleep', seconds).take_none()
|
||||||
|
|
||||||
|
|
||||||
def startTimer(timeout: LuaNum) -> int:
|
def startTimer(timeout: LuaNum) -> int:
|
||||||
return integer(method('startTimer', timeout))
|
return method('startTimer', timeout).take_int()
|
||||||
|
|
||||||
|
|
||||||
def cancelTimer(timerID: int):
|
def cancelTimer(timerID: int):
|
||||||
return nil(method('cancelTimer', timerID))
|
return method('cancelTimer', timerID).take_none()
|
||||||
|
|
||||||
|
|
||||||
def setAlarm(time: LuaNum) -> int:
|
def setAlarm(time: LuaNum) -> int:
|
||||||
# takes time of the day in hours 0..24
|
# takes time of the day in hours 0..24
|
||||||
# returns integer alarmID
|
# returns integer alarmID
|
||||||
return integer(method('setAlarm', time))
|
return method('setAlarm', time).take_int()
|
||||||
|
|
||||||
|
|
||||||
def cancelAlarm(alarmID: int):
|
def cancelAlarm(alarmID: int):
|
||||||
return nil(method('cancelAlarm', alarmID))
|
return method('cancelAlarm', alarmID).take_none()
|
||||||
|
|
||||||
|
|
||||||
def shutdown():
|
def shutdown():
|
||||||
return nil(method('shutdown'))
|
return method('shutdown').take_none()
|
||||||
|
|
||||||
|
|
||||||
def reboot():
|
def reboot():
|
||||||
return nil(method('reboot'))
|
return method('reboot').take_none()
|
||||||
|
|
|
@ -1,10 +1,8 @@
|
||||||
from typing import List
|
from typing import List
|
||||||
|
|
||||||
from ..rproc import nil, integer, fact_array
|
|
||||||
from ..sess import eval_lua_method_factory
|
from ..sess import eval_lua_method_factory
|
||||||
|
|
||||||
|
|
||||||
array_2d_integer = fact_array(fact_array(integer))
|
|
||||||
method = eval_lua_method_factory('paintutils.')
|
method = eval_lua_method_factory('paintutils.')
|
||||||
|
|
||||||
|
|
||||||
|
@ -20,28 +18,28 @@ __all__ = (
|
||||||
|
|
||||||
|
|
||||||
def parseImage(data: str) -> List[List[int]]:
|
def parseImage(data: str) -> List[List[int]]:
|
||||||
return array_2d_integer(method('parseImage', data))
|
return method('parseImage', data).take_2d_int()
|
||||||
|
|
||||||
|
|
||||||
def loadImage(path: str) -> List[List[int]]:
|
def loadImage(path: str) -> List[List[int]]:
|
||||||
return array_2d_integer(method('loadImage', path))
|
return method('loadImage', path).take_2d_int()
|
||||||
|
|
||||||
|
|
||||||
def drawPixel(x: int, y: int, color: int = None):
|
def drawPixel(x: int, y: int, color: int = None):
|
||||||
return nil(method('drawPixel', x, y, color))
|
return method('drawPixel', x, y, color).take_none()
|
||||||
|
|
||||||
|
|
||||||
def drawLine(startX: int, startY: int, endX: int, endY: int, color: int = None):
|
def drawLine(startX: int, startY: int, endX: int, endY: int, color: int = None):
|
||||||
return nil(method('drawLine', startX, startY, endX, endY, color))
|
return method('drawLine', startX, startY, endX, endY, color).take_none()
|
||||||
|
|
||||||
|
|
||||||
def drawBox(startX: int, startY: int, endX: int, endY: int, color: int = None):
|
def drawBox(startX: int, startY: int, endX: int, endY: int, color: int = None):
|
||||||
return nil(method('drawBox', startX, startY, endX, endY, color))
|
return method('drawBox', startX, startY, endX, endY, color).take_none()
|
||||||
|
|
||||||
|
|
||||||
def drawFilledBox(startX: int, startY: int, endX: int, endY: int, color: int = None):
|
def drawFilledBox(startX: int, startY: int, endX: int, endY: int, color: int = None):
|
||||||
return nil(method('drawFilledBox', startX, startY, endX, endY, color))
|
return method('drawFilledBox', startX, startY, endX, endY, color).take_none()
|
||||||
|
|
||||||
|
|
||||||
def drawImage(image: List[List[int]], xPos: int, yPos: int):
|
def drawImage(image: List[List[int]], xPos: int, yPos: int):
|
||||||
return nil(method('drawImage', image, xPos, yPos))
|
return method('drawImage', image, xPos, yPos).take_none()
|
||||||
|
|
|
@ -2,12 +2,7 @@ from dataclasses import dataclass
|
||||||
from typing import Optional, List, Tuple, Any, Union
|
from typing import Optional, List, Tuple, Any, Union
|
||||||
|
|
||||||
from .mixins import TermMixin, TermTarget
|
from .mixins import TermMixin, TermTarget
|
||||||
from .turtle import craft_result
|
|
||||||
from ..lua import LuaNum, lua_args, return_lua_call
|
from ..lua import LuaNum, lua_args, return_lua_call
|
||||||
from ..rproc import (
|
|
||||||
boolean, nil, integer, string, option_integer, option_string,
|
|
||||||
tuple2_integer, array_string, option_string_bool, flat_try_result,
|
|
||||||
)
|
|
||||||
from ..sess import eval_lua, eval_lua_method_factory
|
from ..sess import eval_lua, eval_lua_method_factory
|
||||||
|
|
||||||
|
|
||||||
|
@ -28,65 +23,65 @@ class BasePeripheral:
|
||||||
|
|
||||||
class CCDrive(BasePeripheral):
|
class CCDrive(BasePeripheral):
|
||||||
def isDiskPresent(self) -> bool:
|
def isDiskPresent(self) -> bool:
|
||||||
return boolean(self._method('isDiskPresent'))
|
return self._method('isDiskPresent').take_bool()
|
||||||
|
|
||||||
def getDiskLabel(self) -> Optional[str]:
|
def getDiskLabel(self) -> Optional[str]:
|
||||||
return option_string(self._method('getDiskLabel'))
|
return self._method('getDiskLabel').take_option_string()
|
||||||
|
|
||||||
def setDiskLabel(self, label: str):
|
def setDiskLabel(self, label: str):
|
||||||
return nil(self._method('setDiskLabel', label))
|
return self._method('setDiskLabel', label).take_none()
|
||||||
|
|
||||||
def hasData(self) -> bool:
|
def hasData(self) -> bool:
|
||||||
return boolean(self._method('hasData'))
|
return self._method('hasData').take_bool()
|
||||||
|
|
||||||
def getMountPath(self) -> Optional[str]:
|
def getMountPath(self) -> Optional[str]:
|
||||||
return option_string(self._method('getMountPath'))
|
return self._method('getMountPath').take_option_string()
|
||||||
|
|
||||||
def hasAudio(self) -> bool:
|
def hasAudio(self) -> bool:
|
||||||
return boolean(self._method('hasAudio'))
|
return self._method('hasAudio').take_bool()
|
||||||
|
|
||||||
def getAudioTitle(self) -> Optional[Union[bool, str]]:
|
def getAudioTitle(self) -> Optional[Union[bool, str]]:
|
||||||
return option_string_bool(self._method('getAudioTitle'))
|
return self._method('getAudioTitle').take_option_string_bool()
|
||||||
|
|
||||||
def playAudio(self):
|
def playAudio(self):
|
||||||
return nil(self._method('playAudio'))
|
return self._method('playAudio').take_none()
|
||||||
|
|
||||||
def stopAudio(self):
|
def stopAudio(self):
|
||||||
return nil(self._method('stopAudio'))
|
return self._method('stopAudio').take_none()
|
||||||
|
|
||||||
def ejectDisk(self):
|
def ejectDisk(self):
|
||||||
return nil(self._method('ejectDisk'))
|
return self._method('ejectDisk').take_none()
|
||||||
|
|
||||||
def getDiskID(self) -> Optional[int]:
|
def getDiskID(self) -> Optional[int]:
|
||||||
return option_integer(self._method('getDiskID'))
|
return self._method('getDiskID').take_option_int()
|
||||||
|
|
||||||
|
|
||||||
class CCMonitor(BasePeripheral, TermMixin):
|
class CCMonitor(BasePeripheral, TermMixin):
|
||||||
def getTextScale(self) -> int:
|
def getTextScale(self) -> int:
|
||||||
return integer(self._method('getTextScale'))
|
return self._method('getTextScale').take_int()
|
||||||
|
|
||||||
def setTextScale(self, scale: int):
|
def setTextScale(self, scale: int):
|
||||||
return nil(self._method('setTextScale', scale))
|
return self._method('setTextScale', scale).take_none()
|
||||||
|
|
||||||
|
|
||||||
class ComputerMixin:
|
class ComputerMixin:
|
||||||
def turnOn(self):
|
def turnOn(self):
|
||||||
return nil(self._method('turnOn'))
|
return self._method('turnOn').take_none()
|
||||||
|
|
||||||
def shutdown(self):
|
def shutdown(self):
|
||||||
return nil(self._method('shutdown'))
|
return self._method('shutdown').take_none()
|
||||||
|
|
||||||
def reboot(self):
|
def reboot(self):
|
||||||
return nil(self._method('reboot'))
|
return self._method('reboot').take_none()
|
||||||
|
|
||||||
def getID(self) -> int:
|
def getID(self) -> int:
|
||||||
return integer(self._method('getID'))
|
return self._method('getID').take_int()
|
||||||
|
|
||||||
def getLabel(self) -> Optional[str]:
|
def getLabel(self) -> Optional[str]:
|
||||||
return option_string(self._method('getLabel'))
|
return self._method('getLabel').take_option_string()
|
||||||
|
|
||||||
def isOn(self) -> bool:
|
def isOn(self) -> bool:
|
||||||
return boolean(self._method('isOn'))
|
return self._method('isOn').take_bool()
|
||||||
|
|
||||||
|
|
||||||
class CCComputer(BasePeripheral, ComputerMixin):
|
class CCComputer(BasePeripheral, ComputerMixin):
|
||||||
|
@ -106,22 +101,22 @@ class ModemMessage:
|
||||||
|
|
||||||
class ModemMixin:
|
class ModemMixin:
|
||||||
def isOpen(self, channel: int) -> bool:
|
def isOpen(self, channel: int) -> bool:
|
||||||
return boolean(self._method('isOpen', channel))
|
return self._method('isOpen', channel).take_bool()
|
||||||
|
|
||||||
def open(self, channel: int):
|
def open(self, channel: int):
|
||||||
return nil(self._method('open', channel))
|
return self._method('open', channel).take_none()
|
||||||
|
|
||||||
def close(self, channel: int):
|
def close(self, channel: int):
|
||||||
return nil(self._method('close', channel))
|
return self._method('close', channel).take_none()
|
||||||
|
|
||||||
def closeAll(self):
|
def closeAll(self):
|
||||||
return nil(self._method('closeAll'))
|
return self._method('closeAll').take_none()
|
||||||
|
|
||||||
def transmit(self, channel: int, replyChannel: int, message: Any):
|
def transmit(self, channel: int, replyChannel: int, message: Any):
|
||||||
return nil(self._method('transmit', channel, replyChannel, message))
|
return self._method('transmit', channel, replyChannel, message).take_none()
|
||||||
|
|
||||||
def isWireless(self) -> bool:
|
def isWireless(self) -> bool:
|
||||||
return boolean(self._method('isWireless'))
|
return self._method('isWireless').take_bool()
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def _side(self):
|
def _side(self):
|
||||||
|
@ -151,16 +146,16 @@ class CCWirelessModem(BasePeripheral, ModemMixin):
|
||||||
|
|
||||||
class CCWiredModem(BasePeripheral, ModemMixin):
|
class CCWiredModem(BasePeripheral, ModemMixin):
|
||||||
def getNameLocal(self) -> Optional[str]:
|
def getNameLocal(self) -> Optional[str]:
|
||||||
return option_string(self._method('getNameLocal'))
|
return self._method('getNameLocal').take_option_string()
|
||||||
|
|
||||||
def getNamesRemote(self) -> List[str]:
|
def getNamesRemote(self) -> List[str]:
|
||||||
return array_string(self._method('getNamesRemote'))
|
return self._method('getNamesRemote').take_list_of_strings()
|
||||||
|
|
||||||
def getTypeRemote(self, peripheralName: str) -> Optional[str]:
|
def getTypeRemote(self, peripheralName: str) -> Optional[str]:
|
||||||
return option_string(self._method('getTypeRemote', peripheralName))
|
return self._method('getTypeRemote', peripheralName).take_option_string()
|
||||||
|
|
||||||
def isPresentRemote(self, peripheralName: str) -> bool:
|
def isPresentRemote(self, peripheralName: str) -> bool:
|
||||||
return boolean(self._method('isPresentRemote', peripheralName))
|
return self._method('isPresentRemote', peripheralName).take_bool()
|
||||||
|
|
||||||
def wrapRemote(self, peripheralName: str) -> Optional[BasePeripheral]:
|
def wrapRemote(self, peripheralName: str) -> Optional[BasePeripheral]:
|
||||||
# use instead getMethodsRemote and callRemote
|
# use instead getMethodsRemote and callRemote
|
||||||
|
@ -180,31 +175,33 @@ class CCWiredModem(BasePeripheral, ModemMixin):
|
||||||
|
|
||||||
class CCPrinter(BasePeripheral):
|
class CCPrinter(BasePeripheral):
|
||||||
def newPage(self) -> bool:
|
def newPage(self) -> bool:
|
||||||
return boolean(self._method('newPage'))
|
return self._method('newPage').take_bool()
|
||||||
|
|
||||||
def endPage(self) -> bool:
|
def endPage(self) -> bool:
|
||||||
return boolean(self._method('endPage'))
|
return self._method('endPage').take_bool()
|
||||||
|
|
||||||
def write(self, text: str):
|
def write(self, text: str):
|
||||||
return nil(self._method('write', text))
|
return self._method('write', text).take_none()
|
||||||
|
|
||||||
def setCursorPos(self, x: int, y: int):
|
def setCursorPos(self, x: int, y: int):
|
||||||
return nil(self._method('setCursorPos', x, y))
|
return self._method('setCursorPos', x, y).take_none()
|
||||||
|
|
||||||
def getCursorPos(self) -> Tuple[int, int]:
|
def getCursorPos(self) -> Tuple[int, int]:
|
||||||
return tuple2_integer(self._method('getCursorPos'))
|
rp = self._method('getCursorPos')
|
||||||
|
return tuple(rp.take_int() for _ in range(2))
|
||||||
|
|
||||||
def getPageSize(self) -> Tuple[int, int]:
|
def getPageSize(self) -> Tuple[int, int]:
|
||||||
return tuple2_integer(self._method('getPageSize'))
|
rp = self._method('getPageSize')
|
||||||
|
return tuple(rp.take_int() for _ in range(2))
|
||||||
|
|
||||||
def setPageTitle(self, title: str):
|
def setPageTitle(self, title: str):
|
||||||
return nil(self._method('setPageTitle', title))
|
return self._method('setPageTitle', title).take_none()
|
||||||
|
|
||||||
def getPaperLevel(self) -> int:
|
def getPaperLevel(self) -> int:
|
||||||
return integer(self._method('getPaperLevel'))
|
return self._method('getPaperLevel').take_int()
|
||||||
|
|
||||||
def getInkLevel(self) -> int:
|
def getInkLevel(self) -> int:
|
||||||
return integer(self._method('getInkLevel'))
|
return self._method('getInkLevel').take_int()
|
||||||
|
|
||||||
|
|
||||||
class CCSpeaker(BasePeripheral):
|
class CCSpeaker(BasePeripheral):
|
||||||
|
@ -229,28 +226,28 @@ class CCSpeaker(BasePeripheral):
|
||||||
|
|
||||||
# volume 0..3
|
# volume 0..3
|
||||||
# pitch 0..24
|
# pitch 0..24
|
||||||
return boolean(self._method('playNote', instrument, volume, pitch))
|
return self._method('playNote', instrument, volume, pitch).take_bool()
|
||||||
|
|
||||||
def playSound(self, sound: str, volume: int = 1, pitch: int = 1):
|
def playSound(self, sound: str, volume: int = 1, pitch: int = 1) -> bool:
|
||||||
# volume 0..3
|
# volume 0..3
|
||||||
# pitch 0..2
|
# pitch 0..2
|
||||||
return boolean(self._method('playSound', sound, volume, pitch))
|
return self._method('playSound', sound, volume, pitch).take_bool()
|
||||||
|
|
||||||
|
|
||||||
class CCCommandBlock(BasePeripheral):
|
class CCCommandBlock(BasePeripheral):
|
||||||
def getCommand(self) -> str:
|
def getCommand(self) -> str:
|
||||||
return string(self._method('getCommand'))
|
return self._method('getCommand').take_string()
|
||||||
|
|
||||||
def setCommand(self, command: str):
|
def setCommand(self, command: str):
|
||||||
return nil(self._method('setCommand', command))
|
return self._method('setCommand', command).take_none()
|
||||||
|
|
||||||
def runCommand(self):
|
def runCommand(self):
|
||||||
return flat_try_result(self._method('runCommand'))
|
return self._method('runCommand').check_bool_error()
|
||||||
|
|
||||||
|
|
||||||
class CCWorkbench(BasePeripheral):
|
class CCWorkbench(BasePeripheral):
|
||||||
def craft(self, quantity: int = 64) -> bool:
|
def craft(self, quantity: int = 64) -> bool:
|
||||||
return craft_result(self._method('craft', quantity))
|
return self._method('craft', quantity).bool_error_exclude('No matching recipes')
|
||||||
|
|
||||||
|
|
||||||
TYPE_MAP = {
|
TYPE_MAP = {
|
||||||
|
@ -278,15 +275,15 @@ __all__ = (
|
||||||
|
|
||||||
|
|
||||||
def isPresent(side: str) -> bool:
|
def isPresent(side: str) -> bool:
|
||||||
return boolean(method('isPresent', side))
|
return method('isPresent', side).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def getType(side: str) -> Optional[str]:
|
def getType(side: str) -> Optional[str]:
|
||||||
return option_string(method('getType', side))
|
return method('getType', side).take_option_string()
|
||||||
|
|
||||||
|
|
||||||
def getNames() -> List[str]:
|
def getNames() -> List[str]:
|
||||||
return array_string(method('getNames'))
|
return method('getNames').take_list_of_strings()
|
||||||
|
|
||||||
|
|
||||||
# use instead getMethods and call
|
# use instead getMethods and call
|
||||||
|
@ -298,7 +295,7 @@ def wrap(side: str) -> Optional[BasePeripheral]:
|
||||||
m = 'peripheral.call'
|
m = 'peripheral.call'
|
||||||
|
|
||||||
if ptype == 'modem':
|
if ptype == 'modem':
|
||||||
if boolean(method('call', side, 'isWireless')):
|
if method('call', side, 'isWireless').take_bool():
|
||||||
return CCWirelessModem(m, side)
|
return CCWirelessModem(m, side)
|
||||||
else:
|
else:
|
||||||
return CCWiredModem(m, side)
|
return CCWiredModem(m, side)
|
||||||
|
|
|
@ -1,4 +1,3 @@
|
||||||
from ..rproc import flat_try_result
|
|
||||||
from ..sess import eval_lua_method_factory
|
from ..sess import eval_lua_method_factory
|
||||||
|
|
||||||
|
|
||||||
|
@ -12,8 +11,8 @@ __all__ = (
|
||||||
|
|
||||||
|
|
||||||
def equipBack():
|
def equipBack():
|
||||||
return flat_try_result(method('equipBack'))
|
return method('equipBack').check_bool_error()
|
||||||
|
|
||||||
|
|
||||||
def unequipBack():
|
def unequipBack():
|
||||||
return flat_try_result(method('unequipBack'))
|
return method('unequipBack').check_bool_error()
|
||||||
|
|
|
@ -1,16 +1,9 @@
|
||||||
from typing import Any, List, Optional, Tuple, Union
|
from typing import Any, List, Optional, Tuple, Union
|
||||||
|
|
||||||
from ..lua import LuaNum
|
from ..lua import LuaNum
|
||||||
from ..rproc import nil, integer, option_string, boolean, array_integer, option_integer, fact_option, fact_tuple
|
|
||||||
from ..sess import eval_lua_method_factory
|
from ..sess import eval_lua_method_factory
|
||||||
|
|
||||||
|
|
||||||
recv_result = fact_option(fact_tuple(
|
|
||||||
integer,
|
|
||||||
lambda v: v,
|
|
||||||
option_string,
|
|
||||||
tail_nils=1,
|
|
||||||
))
|
|
||||||
method = eval_lua_method_factory('rednet.')
|
method = eval_lua_method_factory('rednet.')
|
||||||
|
|
||||||
|
|
||||||
|
@ -34,46 +27,47 @@ CHANNEL_BROADCAST = 65535
|
||||||
|
|
||||||
|
|
||||||
def open(side: str):
|
def open(side: str):
|
||||||
return nil(method('open', side))
|
return method('open', side).take_none()
|
||||||
|
|
||||||
|
|
||||||
def close(side: str = None):
|
def close(side: str = None):
|
||||||
return nil(method('close', side))
|
return method('close', side).take_none()
|
||||||
|
|
||||||
|
|
||||||
def send(receiverID: int, message: Any, protocol: str = None) -> bool:
|
def send(receiverID: int, message: Any, protocol: str = None) -> bool:
|
||||||
return boolean(method('send', receiverID, message, protocol))
|
return method('send', receiverID, message, protocol).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def broadcast(message: Any, protocol: str = None):
|
def broadcast(message: Any, protocol: str = None):
|
||||||
return nil(method('broadcast', message, protocol))
|
return method('broadcast', message, protocol).take_none()
|
||||||
|
|
||||||
|
|
||||||
def receive(
|
def receive(
|
||||||
protocolFilter: str = None, timeout: LuaNum = None,
|
protocolFilter: str = None, timeout: LuaNum = None,
|
||||||
) -> Optional[Tuple[int, Any, Optional[str]]]:
|
) -> Optional[Tuple[int, Any, Optional[str]]]:
|
||||||
return recv_result(method('receive', protocolFilter, timeout))
|
rp = method('receive', protocolFilter, timeout)
|
||||||
|
if rp.peek() is None:
|
||||||
|
return None
|
||||||
|
return (rp.take_int(), rp.take(), rp.take_option_string())
|
||||||
|
|
||||||
|
|
||||||
def isOpen(side: str = None) -> bool:
|
def isOpen(side: str = None) -> bool:
|
||||||
return boolean(method('isOpen', side))
|
return method('isOpen', side).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def host(protocol: str, hostname: str):
|
def host(protocol: str, hostname: str):
|
||||||
return nil(method('host', protocol, hostname))
|
return method('host', protocol, hostname).take_none()
|
||||||
|
|
||||||
|
|
||||||
def unhost(protocol: str):
|
def unhost(protocol: str):
|
||||||
return nil(method('unhost', protocol))
|
return method('unhost', protocol).take_none()
|
||||||
|
|
||||||
|
|
||||||
def lookup(protocol: str, hostname: str = None) -> Union[Optional[int], List[int]]:
|
def lookup(protocol: str, hostname: str = None) -> Union[Optional[int], List[int]]:
|
||||||
result = method('lookup', protocol, hostname)
|
rp = method('lookup', protocol, hostname)
|
||||||
if hostname is None:
|
if hostname is None:
|
||||||
if result is None:
|
if rp.peek() is None:
|
||||||
return []
|
return []
|
||||||
if isinstance(result, list):
|
return rp.take_list_of_ints()
|
||||||
return array_integer(result)
|
|
||||||
return [integer(result)]
|
|
||||||
else:
|
else:
|
||||||
return option_integer(result)
|
return rp.take_option_int()
|
||||||
|
|
|
@ -1,6 +1,5 @@
|
||||||
from typing import List
|
from typing import List
|
||||||
|
|
||||||
from ..rproc import boolean, nil, integer, array_string
|
|
||||||
from ..sess import eval_lua_method_factory
|
from ..sess import eval_lua_method_factory
|
||||||
|
|
||||||
|
|
||||||
|
@ -23,46 +22,46 @@ __all__ = (
|
||||||
|
|
||||||
|
|
||||||
def getSides() -> List[str]:
|
def getSides() -> List[str]:
|
||||||
return array_string(method('getSides'))
|
return method('getSides').take_list_of_strings()
|
||||||
|
|
||||||
|
|
||||||
def getInput(side: str) -> bool:
|
def getInput(side: str) -> bool:
|
||||||
return boolean(method('getInput', side))
|
return method('getInput', side).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def setOutput(side: str, value: bool):
|
def setOutput(side: str, value: bool):
|
||||||
return nil(method('setOutput', side, value))
|
return method('setOutput', side, value).take_none()
|
||||||
|
|
||||||
|
|
||||||
def getOutput(side: str) -> bool:
|
def getOutput(side: str) -> bool:
|
||||||
return boolean(method('getOutput', side))
|
return method('getOutput', side).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def getAnalogInput(side: str) -> int:
|
def getAnalogInput(side: str) -> int:
|
||||||
return integer(method('getAnalogInput', side))
|
return method('getAnalogInput', side).take_int()
|
||||||
|
|
||||||
|
|
||||||
def setAnalogOutput(side: str, strength: int):
|
def setAnalogOutput(side: str, strength: int):
|
||||||
return nil(method('setAnalogOutput', side, strength))
|
return method('setAnalogOutput', side, strength).take_none()
|
||||||
|
|
||||||
|
|
||||||
def getAnalogOutput(side: str) -> int:
|
def getAnalogOutput(side: str) -> int:
|
||||||
return integer(method('getAnalogOutput', side))
|
return method('getAnalogOutput', side).take_int()
|
||||||
|
|
||||||
|
|
||||||
# bundled cables are not available in vanilla
|
# bundled cables are not available in vanilla
|
||||||
|
|
||||||
def getBundledInput(side: str) -> int:
|
def getBundledInput(side: str) -> int:
|
||||||
return integer(method('getBundledInput', side))
|
return method('getBundledInput', side).take_int()
|
||||||
|
|
||||||
|
|
||||||
def setBundledOutput(side: str, colors: int):
|
def setBundledOutput(side: str, colors: int):
|
||||||
return nil(method('setBundledOutput', side, colors))
|
return method('setBundledOutput', side, colors).take_none()
|
||||||
|
|
||||||
|
|
||||||
def getBundledOutput(side: str) -> int:
|
def getBundledOutput(side: str) -> int:
|
||||||
return integer(method('getBundledOutput', side))
|
return method('getBundledOutput', side).take_int()
|
||||||
|
|
||||||
|
|
||||||
def testBundledInput(side: str, color: int) -> bool:
|
def testBundledInput(side: str, color: int) -> bool:
|
||||||
return boolean(method('testBundledInput', side, color))
|
return method('testBundledInput', side, color).take_bool()
|
||||||
|
|
|
@ -1,17 +1,8 @@
|
||||||
from typing import Any, List
|
from typing import Any, List
|
||||||
|
|
||||||
from ..rproc import nil, boolean, string, array_string, fact_scheme_dict
|
|
||||||
from ..sess import eval_lua_method_factory
|
from ..sess import eval_lua_method_factory
|
||||||
|
|
||||||
|
|
||||||
setting = fact_scheme_dict({
|
|
||||||
'changed': boolean,
|
|
||||||
}, {
|
|
||||||
'description': string,
|
|
||||||
'default': lambda v: v,
|
|
||||||
'type': string,
|
|
||||||
'value': lambda v: v,
|
|
||||||
})
|
|
||||||
method = eval_lua_method_factory('settings.')
|
method = eval_lua_method_factory('settings.')
|
||||||
|
|
||||||
|
|
||||||
|
@ -37,40 +28,57 @@ def define(name: str, description: str = None, default: Any = None, type: str =
|
||||||
options['default'] = default
|
options['default'] = default
|
||||||
if type is not None:
|
if type is not None:
|
||||||
options['type'] = type
|
options['type'] = type
|
||||||
return nil(method('define', name, options))
|
return method('define', name, options).take_none()
|
||||||
|
|
||||||
|
|
||||||
def undefine(name: str):
|
def undefine(name: str):
|
||||||
return nil(method('undefine', name))
|
return method('undefine', name).take_none()
|
||||||
|
|
||||||
|
|
||||||
def getDetails(name: str) -> dict:
|
def getDetails(name: str) -> dict:
|
||||||
return setting(method('getDetails', name))
|
tp = method('getDetails', name).take_dict((
|
||||||
|
b'changed',
|
||||||
|
b'description',
|
||||||
|
b'default',
|
||||||
|
b'type',
|
||||||
|
b'value',
|
||||||
|
))
|
||||||
|
r = {}
|
||||||
|
r['changed'] = tp.take_bool()
|
||||||
|
for k, v in [
|
||||||
|
('description', tp.take_option_string()),
|
||||||
|
('default', tp.take()),
|
||||||
|
('type', tp.take_option_string()),
|
||||||
|
('value', tp.take()),
|
||||||
|
]:
|
||||||
|
if v is not None:
|
||||||
|
r[k] = v
|
||||||
|
return r
|
||||||
|
|
||||||
|
|
||||||
def set(name: str, value: Any):
|
def set(name: str, value: Any):
|
||||||
return nil(method('set', name, value))
|
return method('set', name, value).take_none()
|
||||||
|
|
||||||
|
|
||||||
def get(name: str, default: Any = None) -> Any:
|
def get(name: str, default: Any = None) -> Any:
|
||||||
return method('get', name, default)
|
return method('get', name, default).take()
|
||||||
|
|
||||||
|
|
||||||
def unset(name: str):
|
def unset(name: str):
|
||||||
return nil(method('unset', name))
|
return method('unset', name).take_none()
|
||||||
|
|
||||||
|
|
||||||
def clear():
|
def clear():
|
||||||
return nil(method('clear'))
|
return method('clear').take_none()
|
||||||
|
|
||||||
|
|
||||||
def getNames() -> List[str]:
|
def getNames() -> List[str]:
|
||||||
return array_string(method('getNames'))
|
return method('getNames').take_list_of_strings()
|
||||||
|
|
||||||
|
|
||||||
def load(path: str = None) -> bool:
|
def load(path: str = None) -> bool:
|
||||||
return boolean(method('load', path))
|
return method('load', path).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def save(path: str = None) -> bool:
|
def save(path: str = None) -> bool:
|
||||||
return boolean(method('save', path))
|
return method('save', path).take_bool()
|
||||||
|
|
|
@ -1,10 +1,8 @@
|
||||||
from typing import List, Dict, Optional
|
from typing import List, Dict, Optional
|
||||||
|
|
||||||
from ..rproc import nil, string, boolean, integer, array_string, fact_mono_dict, option_string
|
|
||||||
from ..sess import eval_lua_method_factory
|
from ..sess import eval_lua_method_factory
|
||||||
|
|
||||||
|
|
||||||
map_string_string = fact_mono_dict(string, string)
|
|
||||||
method = eval_lua_method_factory('shell.')
|
method = eval_lua_method_factory('shell.')
|
||||||
|
|
||||||
|
|
||||||
|
@ -31,75 +29,76 @@ __all__ = (
|
||||||
|
|
||||||
|
|
||||||
def exit():
|
def exit():
|
||||||
return nil(method('exit'))
|
return method('exit').take_none()
|
||||||
|
|
||||||
|
|
||||||
def dir() -> str:
|
def dir() -> str:
|
||||||
return string(method('dir'))
|
return method('dir').take_string()
|
||||||
|
|
||||||
|
|
||||||
def setDir(path: str):
|
def setDir(path: str):
|
||||||
return nil(method('setDir', path))
|
return method('setDir', path).take_none()
|
||||||
|
|
||||||
|
|
||||||
def path() -> str:
|
def path() -> str:
|
||||||
return string(method('path'))
|
return method('path').take_string()
|
||||||
|
|
||||||
|
|
||||||
def setPath(path: str):
|
def setPath(path: str):
|
||||||
return nil(method('setPath', path))
|
return method('setPath', path).take_none()
|
||||||
|
|
||||||
|
|
||||||
def resolve(localPath: str) -> str:
|
def resolve(localPath: str) -> str:
|
||||||
return string(method('resolve', localPath))
|
return method('resolve', localPath).take_string()
|
||||||
|
|
||||||
|
|
||||||
def resolveProgram(name: str) -> Optional[str]:
|
def resolveProgram(name: str) -> Optional[str]:
|
||||||
return option_string(method('resolveProgram', name))
|
return method('resolveProgram', name).take_option_string()
|
||||||
|
|
||||||
|
|
||||||
def aliases() -> Dict[str, str]:
|
def aliases() -> Dict[str, str]:
|
||||||
return map_string_string(method('aliases'))
|
d = method('aliases').take_dict()
|
||||||
|
return {k.decode('latin1'): v.decode('latin1') for k, v in d.items()}
|
||||||
|
|
||||||
|
|
||||||
def setAlias(alias: str, program: str):
|
def setAlias(alias: str, program: str):
|
||||||
return nil(method('setAlias', alias, program))
|
return method('setAlias', alias, program).take_none()
|
||||||
|
|
||||||
|
|
||||||
def clearAlias(alias: str):
|
def clearAlias(alias: str):
|
||||||
return nil(method('clearAlias', alias))
|
return method('clearAlias', alias).take_none()
|
||||||
|
|
||||||
|
|
||||||
def programs(showHidden: bool = None) -> List[str]:
|
def programs(showHidden: bool = None) -> List[str]:
|
||||||
return array_string(method('programs', showHidden))
|
return method('programs', showHidden).take_list_of_strings()
|
||||||
|
|
||||||
|
|
||||||
def getRunningProgram() -> str:
|
def getRunningProgram() -> str:
|
||||||
return string(method('getRunningProgram'))
|
return method('getRunningProgram').take_string()
|
||||||
|
|
||||||
|
|
||||||
def run(command: str, *args: str) -> bool:
|
def run(command: str, *args: str) -> bool:
|
||||||
return boolean(method('run', command, *args))
|
return method('run', command, *args).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def execute(command: str, *args: str) -> bool:
|
def execute(command: str, *args: str) -> bool:
|
||||||
return boolean(method('execute', command, *args))
|
return method('execute', command, *args).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def openTab(command: str, *args: str) -> int:
|
def openTab(command: str, *args: str) -> int:
|
||||||
return integer(method('openTab', command, *args))
|
return method('openTab', command, *args).take_int()
|
||||||
|
|
||||||
|
|
||||||
def switchTab(tabID: int):
|
def switchTab(tabID: int):
|
||||||
return nil(method('switchTab', tabID))
|
return method('switchTab', tabID).take_none()
|
||||||
|
|
||||||
|
|
||||||
def complete(prefix: str) -> List[str]:
|
def complete(prefix: str) -> List[str]:
|
||||||
return array_string(method('complete', prefix))
|
return method('complete', prefix).take_list_of_strings()
|
||||||
|
|
||||||
|
|
||||||
def completeProgram(prefix: str) -> List[str]:
|
def completeProgram(prefix: str) -> List[str]:
|
||||||
return array_string(method('completeProgram', prefix))
|
return method('completeProgram', prefix).take_list_of_strings()
|
||||||
|
|
||||||
# TODO: ?
|
# TODO: ?
|
||||||
# these functions won't be implemented
|
# these functions won't be implemented
|
||||||
|
|
|
@ -4,7 +4,6 @@ from typing import Tuple
|
||||||
from .base import BaseSubAPI
|
from .base import BaseSubAPI
|
||||||
from .mixins import TermMixin, TermTarget
|
from .mixins import TermMixin, TermTarget
|
||||||
from ..lua import lua_call
|
from ..lua import lua_call
|
||||||
from ..rproc import tuple3_number
|
|
||||||
from ..sess import eval_lua_method_factory, lua_context_object
|
from ..sess import eval_lua_method_factory, lua_context_object
|
||||||
|
|
||||||
|
|
||||||
|
@ -61,7 +60,8 @@ setPaletteColor = tapi.setPaletteColor
|
||||||
|
|
||||||
|
|
||||||
def nativePaletteColor(colorID: int) -> Tuple[float, float, float]:
|
def nativePaletteColor(colorID: int) -> Tuple[float, float, float]:
|
||||||
return tuple3_number(method('nativePaletteColor', colorID))
|
rp = method('nativePaletteColor', colorID)
|
||||||
|
return tuple(rp.take_number() for _ in range(3))
|
||||||
|
|
||||||
|
|
||||||
@contextmanager
|
@contextmanager
|
||||||
|
|
|
@ -1,7 +1,6 @@
|
||||||
from typing import List, Union
|
from typing import List, Union
|
||||||
|
|
||||||
from ..lua import LuaNum
|
from ..lua import LuaNum
|
||||||
from ..rproc import nil, string, integer
|
|
||||||
from ..sess import eval_lua_method_factory
|
from ..sess import eval_lua_method_factory
|
||||||
|
|
||||||
|
|
||||||
|
@ -20,27 +19,27 @@ __all__ = (
|
||||||
|
|
||||||
|
|
||||||
def slowWrite(text: str, rate: LuaNum = None):
|
def slowWrite(text: str, rate: LuaNum = None):
|
||||||
return nil(method('slowWrite', text, rate))
|
return method('slowWrite', text, rate).take_none()
|
||||||
|
|
||||||
|
|
||||||
def slowPrint(text: str, rate: LuaNum = None):
|
def slowPrint(text: str, rate: LuaNum = None):
|
||||||
return nil(method('slowPrint', text, rate))
|
return method('slowPrint', text, rate).take_none()
|
||||||
|
|
||||||
|
|
||||||
def formatTime(time: LuaNum, twentyFourHour: bool = None) -> str:
|
def formatTime(time: LuaNum, twentyFourHour: bool = None) -> str:
|
||||||
return string(method('formatTime', time, twentyFourHour))
|
return method('formatTime', time, twentyFourHour).take_string()
|
||||||
|
|
||||||
|
|
||||||
def tabulate(*rows_and_colors: Union[list, int]):
|
def tabulate(*rows_and_colors: Union[list, int]):
|
||||||
return nil(method('tabulate', *rows_and_colors))
|
return method('tabulate', *rows_and_colors).take_none()
|
||||||
|
|
||||||
|
|
||||||
def pagedTabulate(*rows_and_colors: Union[list, int]):
|
def pagedTabulate(*rows_and_colors: Union[list, int]):
|
||||||
return nil(method('pagedTabulate', *rows_and_colors))
|
return method('pagedTabulate', *rows_and_colors).take_none()
|
||||||
|
|
||||||
|
|
||||||
def pagedPrint(text: str, freeLines: int = None) -> int:
|
def pagedPrint(text: str, freeLines: int = None) -> int:
|
||||||
return integer(method('pagedPrint', text, freeLines))
|
return method('pagedPrint', text, freeLines).take_int()
|
||||||
|
|
||||||
|
|
||||||
def complete(partial: str, possible: List[str]) -> List[str]:
|
def complete(partial: str, possible: List[str]) -> List[str]:
|
||||||
|
|
|
@ -1,41 +1,26 @@
|
||||||
from typing import Optional
|
from typing import Optional
|
||||||
|
|
||||||
from ..errors import LuaException
|
from ..errors import LuaException
|
||||||
from ..rproc import integer, boolean, fact_option, any_dict, flat_try_result
|
|
||||||
from ..sess import eval_lua_method_factory
|
from ..sess import eval_lua_method_factory
|
||||||
|
|
||||||
|
|
||||||
method = eval_lua_method_factory('turtle.')
|
method = eval_lua_method_factory('turtle.')
|
||||||
option_any_dict = fact_option(any_dict)
|
|
||||||
|
|
||||||
|
|
||||||
def inspect_result(r):
|
def inspect_result(rp):
|
||||||
assert isinstance(r, list)
|
success = rp.take_bool()
|
||||||
assert len(r) == 2
|
|
||||||
success, data = r
|
|
||||||
assert isinstance(success, bool)
|
|
||||||
if not success:
|
if not success:
|
||||||
if data == 'No block to inspect':
|
msg = rp.take_string()
|
||||||
|
if msg == 'No block to inspect':
|
||||||
return None
|
return None
|
||||||
raise LuaException(data)
|
raise LuaException(msg)
|
||||||
else:
|
else:
|
||||||
return any_dict(data)
|
return rp.take_dict()
|
||||||
|
|
||||||
|
|
||||||
def boolean_with_error_exclusion(exclude_msg):
|
def boolean_with_error_exclusion(exclude_msg):
|
||||||
def proc(r):
|
def proc(rp):
|
||||||
if r is True:
|
return rp.bool_error_exclude(exclude_msg)
|
||||||
return True
|
|
||||||
assert isinstance(r, list)
|
|
||||||
assert len(r) == 2
|
|
||||||
success, msg = r
|
|
||||||
assert isinstance(success, bool)
|
|
||||||
if not success:
|
|
||||||
if msg == exclude_msg:
|
|
||||||
return False
|
|
||||||
raise LuaException(msg)
|
|
||||||
else:
|
|
||||||
return True
|
|
||||||
return proc
|
return proc
|
||||||
|
|
||||||
|
|
||||||
|
@ -49,8 +34,8 @@ attack_result = boolean_with_error_exclusion('Nothing to attack here')
|
||||||
craft_result = boolean_with_error_exclusion('No matching recipes')
|
craft_result = boolean_with_error_exclusion('No matching recipes')
|
||||||
|
|
||||||
|
|
||||||
def always_true(r):
|
def always_true(rp):
|
||||||
assert boolean(r) is True
|
assert rp.take_bool() is True
|
||||||
# return value is useless
|
# return value is useless
|
||||||
return None
|
return None
|
||||||
|
|
||||||
|
@ -135,19 +120,22 @@ def select(slotNum: int):
|
||||||
|
|
||||||
|
|
||||||
def getSelectedSlot() -> int:
|
def getSelectedSlot() -> int:
|
||||||
return integer(method('getSelectedSlot'))
|
return method('getSelectedSlot').take_int()
|
||||||
|
|
||||||
|
|
||||||
def getItemCount(slotNum: int = None) -> int:
|
def getItemCount(slotNum: int = None) -> int:
|
||||||
return integer(method('getItemCount', slotNum))
|
return method('getItemCount', slotNum).take_int()
|
||||||
|
|
||||||
|
|
||||||
def getItemSpace(slotNum: int = None) -> int:
|
def getItemSpace(slotNum: int = None) -> int:
|
||||||
return integer(method('getItemSpace', slotNum))
|
return method('getItemSpace', slotNum).take_int()
|
||||||
|
|
||||||
|
|
||||||
def getItemDetail(slotNum: int = None) -> dict:
|
def getItemDetail(slotNum: int = None) -> Optional[dict]:
|
||||||
return option_any_dict(method('getItemDetail', slotNum))
|
rp = method('getItemDetail', slotNum)
|
||||||
|
if rp.peek() is None:
|
||||||
|
return None
|
||||||
|
return rp.take_dict()
|
||||||
|
|
||||||
|
|
||||||
def equipLeft():
|
def equipLeft():
|
||||||
|
@ -195,15 +183,15 @@ def placeDown() -> bool:
|
||||||
|
|
||||||
|
|
||||||
def detect() -> bool:
|
def detect() -> bool:
|
||||||
return boolean(method('detect'))
|
return method('detect').take_bool()
|
||||||
|
|
||||||
|
|
||||||
def detectUp() -> bool:
|
def detectUp() -> bool:
|
||||||
return boolean(method('detectUp'))
|
return method('detectUp').take_bool()
|
||||||
|
|
||||||
|
|
||||||
def detectDown() -> bool:
|
def detectDown() -> bool:
|
||||||
return boolean(method('detectDown'))
|
return method('detectDown').take_bool()
|
||||||
|
|
||||||
|
|
||||||
def inspect() -> Optional[dict]:
|
def inspect() -> Optional[dict]:
|
||||||
|
@ -219,19 +207,19 @@ def inspectDown() -> Optional[dict]:
|
||||||
|
|
||||||
|
|
||||||
def compare() -> bool:
|
def compare() -> bool:
|
||||||
return boolean(method('compare'))
|
return method('compare').take_bool()
|
||||||
|
|
||||||
|
|
||||||
def compareUp() -> bool:
|
def compareUp() -> bool:
|
||||||
return boolean(method('compareUp'))
|
return method('compareUp').take_bool()
|
||||||
|
|
||||||
|
|
||||||
def compareDown() -> bool:
|
def compareDown() -> bool:
|
||||||
return boolean(method('compareDown'))
|
return method('compareDown').take_bool()
|
||||||
|
|
||||||
|
|
||||||
def compareTo(slot: int) -> bool:
|
def compareTo(slot: int) -> bool:
|
||||||
return boolean(method('compareTo', slot))
|
return method('compareTo', slot).take_bool()
|
||||||
|
|
||||||
|
|
||||||
def drop(count: int = None) -> bool:
|
def drop(count: int = None) -> bool:
|
||||||
|
@ -259,15 +247,15 @@ def suckDown(amount: int = None) -> bool:
|
||||||
|
|
||||||
|
|
||||||
def refuel(quantity: int = None):
|
def refuel(quantity: int = None):
|
||||||
return flat_try_result(method('refuel', quantity))
|
return method('refuel', quantity).check_bool_error()
|
||||||
|
|
||||||
|
|
||||||
def getFuelLevel() -> int:
|
def getFuelLevel() -> int:
|
||||||
return integer(method('getFuelLevel'))
|
return method('getFuelLevel').take_int()
|
||||||
|
|
||||||
|
|
||||||
def getFuelLimit() -> int:
|
def getFuelLimit() -> int:
|
||||||
return integer(method('getFuelLimit'))
|
return method('getFuelLimit').take_int()
|
||||||
|
|
||||||
|
|
||||||
def transferTo(slot: int, quantity: int = None) -> bool:
|
def transferTo(slot: int, quantity: int = None) -> bool:
|
||||||
|
|
|
@ -2,7 +2,6 @@ from contextlib import contextmanager
|
||||||
from typing import Tuple
|
from typing import Tuple
|
||||||
|
|
||||||
from ..lua import lua_call
|
from ..lua import lua_call
|
||||||
from ..rproc import nil, tuple2_integer, tuple3_string
|
|
||||||
from ..sess import eval_lua_method_factory, lua_context_object
|
from ..sess import eval_lua_method_factory, lua_context_object
|
||||||
from .base import BaseSubAPI
|
from .base import BaseSubAPI
|
||||||
from .mixins import TermMixin, TermTarget
|
from .mixins import TermMixin, TermTarget
|
||||||
|
@ -10,22 +9,24 @@ from .mixins import TermMixin, TermTarget
|
||||||
|
|
||||||
class CCWindow(BaseSubAPI, TermMixin):
|
class CCWindow(BaseSubAPI, TermMixin):
|
||||||
def setVisible(self, visibility: bool):
|
def setVisible(self, visibility: bool):
|
||||||
return nil(self._method('setVisible', visibility))
|
return self._method('setVisible', visibility).take_none()
|
||||||
|
|
||||||
def redraw(self):
|
def redraw(self):
|
||||||
return nil(self._method('redraw'))
|
return self._method('redraw').take_none()
|
||||||
|
|
||||||
def restoreCursor(self):
|
def restoreCursor(self):
|
||||||
return nil(self._method('restoreCursor'))
|
return self._method('restoreCursor').take_none()
|
||||||
|
|
||||||
def getPosition(self) -> Tuple[int, int]:
|
def getPosition(self) -> Tuple[int, int]:
|
||||||
return tuple2_integer(self._method('getPosition'))
|
rp = self._method('getPosition')
|
||||||
|
return tuple(rp.take_int() for _ in range(2))
|
||||||
|
|
||||||
def reposition(self, x: int, y: int, width: int = None, height: int = None, parent: TermTarget = None):
|
def reposition(self, x: int, y: int, width: int = None, height: int = None, parent: TermTarget = None):
|
||||||
return nil(self._method('reposition', x, y, width, height, parent))
|
return self._method('reposition', x, y, width, height, parent).take_none()
|
||||||
|
|
||||||
def getLine(self, y: int) -> Tuple[str, str, str]:
|
def getLine(self, y: int) -> Tuple[str, str, str]:
|
||||||
return tuple3_string(self._method('getLine', y))
|
rp = self._method('getLine', y)
|
||||||
|
return tuple(rp.take_string() for _ in range(3))
|
||||||
|
|
||||||
def get_term_target(self) -> TermTarget:
|
def get_term_target(self) -> TermTarget:
|
||||||
return TermTarget(self.get_expr_code())
|
return TermTarget(self.get_expr_code())
|
||||||
|
|
|
@ -39,7 +39,7 @@ def step(text):
|
||||||
|
|
||||||
|
|
||||||
def get_object_table(objname):
|
def get_object_table(objname):
|
||||||
r = eval_lua(f"""
|
rp = eval_lua(f"""
|
||||||
local r = {{}}
|
local r = {{}}
|
||||||
for k in pairs({objname}) do
|
for k in pairs({objname}) do
|
||||||
local t = type({objname}[k])
|
local t = type({objname}[k])
|
||||||
|
@ -51,8 +51,12 @@ for k in pairs({objname}) do
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
return r""", immediate=True)
|
return r""", immediate=True)
|
||||||
assert len(r) == 1
|
d = rp.take_dict()
|
||||||
return r[0]
|
return {
|
||||||
|
k1.decode('latin1'): {
|
||||||
|
k2.decode('latin1'): v for k2, v in t.items()
|
||||||
|
} for k1, t in d.items()
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
def get_class_table(cls):
|
def get_class_table(cls):
|
||||||
|
|
|
@ -151,50 +151,32 @@ assert fs.complete('ap', 'tdir', includeFiles=False) == []
|
||||||
|
|
||||||
assert fs.getSize('tdir/banana') == 9
|
assert fs.getSize('tdir/banana') == 9
|
||||||
with fs.open('tdir/banana', 'r') as f:
|
with fs.open('tdir/banana', 'r') as f:
|
||||||
assert _lib.get_object_table(f.get_expr_code()) == {'function': {
|
|
||||||
'close': True,
|
|
||||||
'read': True,
|
|
||||||
'readLine': True,
|
|
||||||
'readAll': True,
|
|
||||||
}}
|
|
||||||
assert f.read(4) == 'text'
|
assert f.read(4) == 'text'
|
||||||
assert f.readLine() == 'line'
|
assert f.readLine() == 'line'
|
||||||
assert f.read(1) is None
|
assert f.read(1) is None
|
||||||
assert f.readLine() is None
|
assert f.readLine() is None
|
||||||
assert f.readAll() == ''
|
assert f.readAll() is None
|
||||||
assert f.readAll() == ''
|
assert f.readAll() is None
|
||||||
assert fs.getSize('tdir/banana') == 9
|
assert fs.getSize('tdir/banana') == 9
|
||||||
with fs.open('tdir/banana', 'a') as f:
|
with fs.open('tdir/banana', 'a') as f:
|
||||||
assert _lib.get_object_table(f.get_expr_code()) == {'function': {
|
|
||||||
'close': True,
|
|
||||||
'write': True,
|
|
||||||
'writeLine': True,
|
|
||||||
'flush': True,
|
|
||||||
}}
|
|
||||||
assert f.write('x') is None
|
assert f.write('x') is None
|
||||||
assert fs.getSize('tdir/banana') == 10
|
assert fs.getSize('tdir/banana') == 10
|
||||||
with fs.open('tdir/banana', 'w') as f:
|
with fs.open('tdir/banana', 'w') as f:
|
||||||
pass
|
pass
|
||||||
assert fs.getSize('tdir/banana') == 0 # truncate
|
assert fs.getSize('tdir/banana') == 0 # truncate
|
||||||
with fs.open('tdir/banana', 'w') as f:
|
with fs.open('tdir/banana', 'w') as f:
|
||||||
assert _lib.get_object_table(f.get_expr_code()) == {'function': {
|
|
||||||
'close': True,
|
|
||||||
'write': True,
|
|
||||||
'writeLine': True,
|
|
||||||
'flush': True,
|
|
||||||
}}
|
|
||||||
assert f.write('Bro') is None
|
assert f.write('Bro') is None
|
||||||
assert f.writeLine('wn fox jumps') is None
|
assert f.writeLine('wn fox jumps') is None
|
||||||
assert fs.getSize('tdir/banana') == 0 # changes are not on a disk
|
# assert fs.getSize('tdir/banana') == 0 # changes are not on a disk
|
||||||
assert f.flush() is None
|
assert f.flush() is None
|
||||||
assert fs.getSize('tdir/banana') == len('Brown fox jumps\n')
|
assert fs.getSize('tdir/banana') == len('Brown fox jumps\n')
|
||||||
assert f.write('ov') is None
|
assert f.write('ov') is None
|
||||||
assert f.write('er ') is None
|
assert f.write('er ') is None
|
||||||
assert f.write('a lazy') is None
|
assert f.write('a lazy') is None
|
||||||
assert f.writeLine(' dog.') is None
|
assert f.writeLine(' дог.') is None
|
||||||
assert fs.getSize('tdir/banana') > 9
|
assert fs.getSize('tdir/banana') > 9
|
||||||
with fs.open('tdir/banana', 'r') as f:
|
with fs.open('tdir/banana', 'r') as f:
|
||||||
assert f.readAll() == 'Brown fox jumps\nover a lazy dog.' # no newline?
|
assert f.readAll() == 'Brown fox jumps\nover a lazy дог.\n'
|
||||||
with assert_raises(LuaException):
|
with assert_raises(LuaException):
|
||||||
with fs.open('tdir/banana', 'rw') as f:
|
with fs.open('tdir/banana', 'rw') as f:
|
||||||
pass
|
pass
|
||||||
|
@ -202,22 +184,19 @@ with assert_raises(LuaException):
|
||||||
assert fs.exists('tdir/banana') is True
|
assert fs.exists('tdir/banana') is True
|
||||||
|
|
||||||
with fs.open('tdir/binfile', 'wb') as f:
|
with fs.open('tdir/binfile', 'wb') as f:
|
||||||
assert f.write('a' * 9) is None
|
assert f.write(b'a' * 9) is None
|
||||||
assert f.seek() == 9
|
assert f.seek() == 9
|
||||||
assert f.seek('set', 0) == 0
|
assert f.seek('set', 0) == 0
|
||||||
assert f.write('b' * 3) is None
|
assert f.write(b'b' * 3) is None
|
||||||
assert f.seek('cur', -1) == 2
|
assert f.seek('cur', -1) == 2
|
||||||
assert f.write('c' * 3) is None
|
assert f.write(b'c' * 3) is None
|
||||||
assert f.seek('end') == 9
|
assert f.seek('end') == 9
|
||||||
assert f.write('d' * 3) is None
|
assert f.write(b'd' * 3) is None
|
||||||
with assert_raises(LuaException):
|
with assert_raises(LuaException):
|
||||||
f.seek('set', -10)
|
f.seek('set', -10)
|
||||||
|
|
||||||
with fs.open('tdir/binfile', 'rb') as f:
|
with fs.open('tdir/binfile', 'rb') as f:
|
||||||
assert f.readAll() == 'bbcccaaaaddd'
|
assert f.readAll() == b'bbcccaaaaddd'
|
||||||
|
|
||||||
with fs.open('tdir/binfile', 'rb') as f:
|
|
||||||
assert isinstance(f.read(), int)
|
|
||||||
|
|
||||||
with fs.open('tdir/binfile', 'r') as f:
|
with fs.open('tdir/binfile', 'r') as f:
|
||||||
assert [line for line in f] == ['bbcccaaaaddd']
|
assert [line for line in f] == ['bbcccaaaaddd']
|
||||||
|
|
|
@ -146,3 +146,5 @@ for _, v in ipairs(roundtrip_tables) do
|
||||||
end
|
end
|
||||||
|
|
||||||
print('ALL OK')
|
print('ALL OK')
|
||||||
|
|
||||||
|
print(serialize({true, false, 'Position is negative'}))
|
||||||
|
|
Loading…
Reference in a new issue