Sitelet https://github.com/lua-stdlib/lua-stdlib/commit/131dd6d1aedbd31c03db1507f5b4aeb6cd855085
Skip to content

Commit 131dd6d

Browse files
committed
base: provide better errors from exported object methods.
* specs/base_spec.yaml (export): Specify behaviour of exported object methods. * lib/std/base.lua (export): Use separator ':' between module name and method name when dealing with methods, as opposed to '.' when dealing with functions. Count method arguments starting at '0' for self in error messages. * build-aux/sanity-cfg.mk (sc_error_message_uppercase): Add specs/base_spec.yaml. Signed-off-by: Gary V. Vaughan <gary@gnu.org>
1 parent a2c9fa8 commit 131dd6d

3 files changed

Lines changed: 38 additions & 2 deletions

File tree

‎build-aux/sanity-cfg.mk‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,3 @@
1-
exclude_file_name_regexp--sc_error_message_uppercase = ^lib/std/(list|optparse).lua|specs/debug_spec.yaml$$
1+
exclude_file_name_regexp--sc_error_message_uppercase = ^lib/std/(list|optparse).lua|specs/(base|debug)_spec.yaml$$
22

33
EXTRA_DIST += build-aux/sanity-cfg.mk

‎lib/std/base.lua‎

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -522,7 +522,7 @@ local function export (M, decl, fn, ...)
522522
argerror (fname, 2, "at least 1 argument type expected, got 0")
523523
end
524524

525-
local name = M[1] .. "." .. name
525+
local name = M[1] .. (M[2] and ":" or ".") .. name
526526

527527
-- If the final element of types ends with "*", then set max to a
528528
-- sentinel value to denote type-checking of *all* remaining
@@ -542,6 +542,13 @@ local function export (M, decl, fn, ...)
542542
local args = {...}
543543
local argc, bestmismatch, at = arglen (args), 0, 0
544544

545+
-- For object methods, report type mismatch on self as argument 0.
546+
if M[2] then
547+
argcheck (name, 0, M[2], args[1], 2)
548+
table.remove (args, 1)
549+
argc = argc - 1
550+
end
551+
545552
for i, types in ipairs (type_specs) do
546553
local mismatch = match (types, args, max == math.huge)
547554
if mismatch == nil then

‎specs/base_spec.yaml‎

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -192,3 +192,32 @@ specify std.base:
192192
- it accepts correct argument types:
193193
expect (chk ("two")).to_equal (MAGIC) -- should be .to_be?
194194
expect (chk (1, "two")).to_equal (MAGIC) -- should be .to_be?
195+
- context when checking self on an object method:
196+
- before:
197+
fake_module = "base_spec.yaml"
198+
M = { fake_module, "Object" }
199+
fname = "chk_method"
200+
msg = function (...)
201+
return badarg (nil, fake_module .. ":" .. fname, ...)
202+
end
203+
f (M, "chk_method (string)", function (self, x) return x end)
204+
Object = require "std.object" {}
205+
Bad = Object { _type = "Bad" }
206+
obj = Object { chk = M.chk_method }
207+
- it diagnoses missing arguments:
208+
expect (obj.chk ()).to_error (msg (0, "Object"))
209+
expect (obj:chk ()).to_error (msg (1, "string"))
210+
- it diagnoses wrong argument types:
211+
expect (obj.chk ({})).to_error (msg (0, "Object", "empty table"))
212+
expect (obj.chk (Bad)).to_error (msg (0, "Object", "Bad"))
213+
expect (obj:chk ({})).to_error (msg (1, "string", "empty table"))
214+
expect (obj:chk (obj)).to_error (msg (1, "string", "Object"))
215+
- it diagnoses too many arguments:
216+
expect (obj.chk (obj, "str", false)).
217+
to_error (toomanyarg (nil, fake_module .. ":" .. fname, 1, 2))
218+
expect (obj:chk ("str", false)).
219+
to_error (toomanyarg (nil, fake_module .. ":" .. fname, 1, 2))
220+
- it accepts correct argument types:
221+
expect (obj.chk (obj, "str")).to_be "str"
222+
expect (obj.chk (Object, "str")).to_be "str"
223+
expect (obj:chk ("str")).to_be "str"

0 commit comments

Comments
 (0)