test.lua 7.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270
  1. local u = require 'luaunit'
  2. local mp = require "mp"
  3. local eq = u.assertEquals
  4. local fail = u.assertErrorMsgContains
  5. local function check_eq(t, t2)
  6. local bytes = mp.encode(t)
  7. local ok, r = pcall(mp.decode, bytes)
  8. if not ok then
  9. print(mp.tohex(bytes))
  10. error(r)
  11. end
  12. eq(mp.decode(bytes), t2 or t)
  13. end
  14. function _G.test_basic()
  15. local a = "\0\1\2\3\4\5\6\7\8\9\10\11\12\13\14\15\16"
  16. eq(mp.fromhex(mp.tohex(a)), a)
  17. eq({mp.decode "\1\2"}, {1,2})
  18. check_eq {
  19. foo = 1,
  20. bar = 2,
  21. array = {1,2,3,4}
  22. }
  23. check_eq {
  24. foo = 1,
  25. bar = 2,
  26. array = mp.array {1,2,3,4}
  27. }
  28. check_eq {
  29. foo = 1,
  30. bar = 2,
  31. array = mp.array {1,2,3,4}
  32. }
  33. check_eq {
  34. foo = 1,
  35. bar = 2,
  36. array = mp.map {1,2,3,4}
  37. }
  38. check_eq {
  39. f1 = 1,
  40. f2 = 2,
  41. fs1 = "foo",
  42. fs2 = "bar",
  43. fm = {
  44. ft1 = 1,
  45. ft2 = "foo",
  46. ft3 = {1,2,3},
  47. ft4 = { ft5 = { ft6 = { ft7 = { ft8 = { ft9 = mp.array { } } } } } }
  48. },
  49. fa_long = {1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17},
  50. fm_long = {
  51. f1 = 1, f2 = 2, f3 = 3, f4 = 4, f5 = 5, f6 = 6, f7 = 7, f8 = 8,
  52. f9 = 9, f10 = 10, f11 = 11, f12 = 12, f13 = 13, f14 = 14, f15 = 15, f16 = 16,
  53. f17 = 17, f18 = 18, f19 = 19, f20 = 20,
  54. }
  55. }
  56. end
  57. function _G.test_boolean()
  58. check_eq(true)
  59. check_eq(false)
  60. end
  61. function _G.test_number()
  62. check_eq(0)
  63. check_eq(127)
  64. check_eq(128)
  65. check_eq(0x100 + 100)
  66. check_eq(0x10000 + 100)
  67. check_eq(0x100000000 + 100)
  68. check_eq(-1)
  69. check_eq(-32)
  70. check_eq(-33)
  71. check_eq(-100)
  72. check_eq(-0x100 - 100)
  73. check_eq(-0x10000 - 100)
  74. check_eq(-0x100000000 - 100)
  75. check_eq("a")
  76. check_eq("aaa")
  77. check_eq(("a"):rep(31))
  78. check_eq(("a"):rep(32))
  79. check_eq(("a"):rep(0x100+100))
  80. check_eq(("a"):rep(0x10000+100))
  81. check_eq(1.123)
  82. check_eq(function() return "u",100 end, 100)
  83. check_eq(function() return "u",200 end, 200)
  84. check_eq(function() return "u",0x100 + 100 end, 0x100 + 100)
  85. check_eq(function() return "u",0x10000 + 100 end, 0x10000 + 100)
  86. check_eq(function() return "u",0x100000000 + 100 end, 0x100000000 + 100)
  87. check_eq(function() return "i",100 end, 100)
  88. check_eq(function() return "i",0x100 + 100 end, 0x100 + 100)
  89. check_eq(function() return "i",0x10000 + 100 end, 0x10000 + 100)
  90. check_eq(function() return "i",0x100000000 + 100 end, 0x100000000 + 100)
  91. check_eq(function() return "f",1.5 end, 1.5)
  92. check_eq(function() return "d",1.5 end, 1.5)
  93. check_eq(mp.meta("int", { value = 1 }), 1)
  94. check_eq(mp.meta("value", { value = 1 }), 1)
  95. end
  96. function _G.test_list()
  97. do
  98. local a = {}
  99. for i = 1, 1000 do
  100. a[#a+1] = i
  101. end
  102. check_eq(a)
  103. for i = 1, 65535 do
  104. a[#a+1] = i
  105. end
  106. check_eq(a)
  107. end
  108. do
  109. local a = {}
  110. for i = 1, 1000 do
  111. a["foo"..i] = i
  112. end
  113. check_eq(a)
  114. for i = 1, 65536 do
  115. a["foo"..(i+1000)] = i
  116. end
  117. check_eq(a)
  118. end
  119. end
  120. function _G.test_nil()
  121. check_eq(nil)
  122. eq(mp.decode(mp.encode(mp.null)), nil)
  123. eq(mp.decode(mp.newencoder()(mp.null)), nil)
  124. eq(tostring(mp.null), "null")
  125. end
  126. function _G.test_ext()
  127. local e = { type = 1, value = "foo" }
  128. local function check_ext(t, v)
  129. check_eq(function() return "e", t, v end, { type = t, value = v })
  130. end
  131. check_ext(1, "a")
  132. check_ext(1, ("a"):rep(2))
  133. check_ext(1, ("a"):rep(4))
  134. check_ext(1, ("a"):rep(8))
  135. check_ext(1, ("a"):rep(16))
  136. check_ext(1, ("a"):rep(50))
  137. check_ext(1, ("a"):rep(30000))
  138. check_ext(1, ("a"):rep(65537))
  139. check_ext(1, ("a"):rep(3))
  140. eq(mp.decode(mp.encode(function() return "e", 1, "foo" end),
  141. nil, nil, function(t, v)
  142. eq(t, 1)
  143. eq(v, "foo")
  144. return v
  145. end), "foo")
  146. eq(mp.decode(mp.encode(function() return "e", 1, "foo" end),
  147. nil, nil, function() end), e)
  148. check_eq(mp.meta("extension", e), e)
  149. --check_eq(mp.meta("t", mp.meta("ext", { value = e })), e)
  150. local e1 = mp.meta("extension", "foo")
  151. e1.type = 1
  152. check_eq(e1, e)
  153. local e2 = mp.meta("extension", setmetatable({type = 1, value = "foo"}, {}))
  154. check_eq(e2, e)
  155. end
  156. function _G.test_handler()
  157. check_eq(function() return "T" end, true)
  158. eq(mp.decode(mp.encode(function() return "F" end)), false)
  159. check_eq(function() return "s", "foo" end, "foo")
  160. check_eq(function() return "b", "foo" end, "foo")
  161. local co = coroutine.create(function()end)
  162. local c = 0
  163. local v = mp.newencoder(function(v, k, t)
  164. assert(k == nil)
  165. assert(t == nil)
  166. if v == co then
  167. c = c + 1
  168. return "int", 1
  169. end
  170. return "nil"
  171. end)(co, co, co)
  172. eq(c, 3); eq(v, "\1\1\1")
  173. c = 0; v = mp.newencoder(function(v, k, t)
  174. assert(k >= 1 and k <= 3)
  175. assert(type(t) == "table")
  176. if v == co then
  177. c = c + 1
  178. return "int", 1
  179. end
  180. return "nil"
  181. end)({co, co, co})
  182. eq(c, 3); eq(v, "\x93\1\1\1")
  183. c = 0; v = mp.newencoder(function(v, k, t)
  184. assert(k == "foo")
  185. assert(type(t) == "table")
  186. if v == co then
  187. c = c + 1
  188. return "int", 1
  189. end
  190. return "nil"
  191. end)({foo = co})
  192. eq(c, 1); eq(v, "\x81\xA3foo\1")
  193. c = 0; v = mp.newencoder(function(v, k, t)
  194. assert(k == nil)
  195. assert(type(t) == "table")
  196. if v == co then
  197. c = c + 1
  198. return "int", 1
  199. end
  200. return "nil"
  201. end)({[co] = "bar"})
  202. eq(c, 1); eq(v, "\x81\1\xA3bar")
  203. end
  204. function _G.test_error()
  205. fail("number expected, got nil",
  206. function() mp.encode(function() return "u", nil end) end)
  207. fail("integer expected, got number",
  208. function() mp.encode(function() return "u", 1.2 end) end)
  209. fail("attempt to index a msgpack.null value",
  210. function() return mp.null.abc end)
  211. fail("attempt to index a msgpack.null value",
  212. function() mp.null.abc = 10 end)
  213. local a = {} a[1] = a
  214. fail("array level too deep", function() mp.encode(a) end)
  215. a = {} a.foo = a
  216. fail("map level too deep", function() mp.encode(a) end)
  217. fail("invalid key in map", function()
  218. mp.encode { [function() end] = 1 }
  219. end)
  220. fail("integer expected for extension type, got boolean", function()
  221. mp.encode(function() return "e", true end)
  222. end)
  223. fail("invalid extension type: 10000", function()
  224. mp.encode(function() return "e", 10000 end)
  225. end)
  226. fail("string expected for extension value, got boolean", function()
  227. mp.encode(function() return "e", 1, true end)
  228. end)
  229. fail("'pack' field expected in handler object", function()
  230. mp.encode(mp.meta("handler", {}))
  231. end)
  232. fail("'value' field expected in wrapper object", function()
  233. mp.encode(mp.meta("int", {}))
  234. end)
  235. fail("invalid type 'thread'", function()
  236. mp.encode(coroutine.create(function() end))
  237. end)
  238. fail("invalid string at offset 2: 1 bytes expected, got 0 bytes",
  239. function() mp.decode("\161") end)
  240. fail("invalid string at offset 2: 1 bytes expected, got 0 bytes",
  241. function() mp.decode("\161") end)
  242. fail("unexpected end of message at offset 2: map key expected",
  243. function() mp.decode("\129") end)
  244. fail("unexpected end of message at offset 3: map value expected",
  245. function() mp.decode("\129\1") end)
  246. fail("unexpected end of message at offset 2: array element expected",
  247. function() mp.decode("\145") end)
  248. fail("invalid char '193' at offset 2",
  249. function() mp.decode("\193") end)
  250. end
  251. if _VERSION == "Lua 5.1" and not _G.jit then
  252. u.LuaUnit.run()
  253. else
  254. os.exit(u.LuaUnit.run(), true)
  255. end
  256. -- unixcc: run='rm -f *.gcda; time lua test.lua; gcov mp.c'
  257. -- win32cc: run='del /s/q *.gcda & lua test.lua & gcov mp.c'