aboutsummaryrefslogtreecommitdiffstats
path: root/tests
diff options
context:
space:
mode:
Diffstat (limited to 'tests')
-rw-r--r--tests/json/fail1.json1
-rw-r--r--tests/json/fail10.json1
-rw-r--r--tests/json/fail11.json1
-rw-r--r--tests/json/fail12.json1
-rw-r--r--tests/json/fail13.json1
-rw-r--r--tests/json/fail14.json1
-rw-r--r--tests/json/fail15.json1
-rw-r--r--tests/json/fail16.json1
-rw-r--r--tests/json/fail17.json1
-rw-r--r--tests/json/fail18.json1
-rw-r--r--tests/json/fail19.json1
-rw-r--r--tests/json/fail2.json1
-rw-r--r--tests/json/fail20.json1
-rw-r--r--tests/json/fail21.json1
-rw-r--r--tests/json/fail22.json1
-rw-r--r--tests/json/fail23.json1
-rw-r--r--tests/json/fail24.json1
-rw-r--r--tests/json/fail25.json1
-rw-r--r--tests/json/fail26.json1
-rw-r--r--tests/json/fail27.json2
-rw-r--r--tests/json/fail28.json2
-rw-r--r--tests/json/fail29.json1
-rw-r--r--tests/json/fail3.json1
-rw-r--r--tests/json/fail30.json1
-rw-r--r--tests/json/fail31.json1
-rw-r--r--tests/json/fail32.json1
-rw-r--r--tests/json/fail33.json1
-rw-r--r--tests/json/fail4.json1
-rw-r--r--tests/json/fail5.json1
-rw-r--r--tests/json/fail6.json1
-rw-r--r--tests/json/fail7.json1
-rw-r--r--tests/json/fail8.json1
-rw-r--r--tests/json/fail9.json1
-rw-r--r--tests/json/pass1.json58
-rw-r--r--tests/json/pass2.json1
-rw-r--r--tests/json/pass3.json6
-rw-r--r--tests/modulemanager_option_conversion.lua4
-rwxr-xr-xtests/run_tests.sh2
-rw-r--r--tests/test.lua61
-rw-r--r--tests/test_core_configmanager.lua30
-rw-r--r--tests/test_core_modulemanager.lua48
-rw-r--r--tests/test_core_s2smanager.lua7
-rw-r--r--tests/test_core_stanza_router.lua44
-rw-r--r--tests/test_net_http_parser.lua47
-rw-r--r--tests/test_sasl.lua4
-rw-r--r--tests/test_utf8.lua3
-rw-r--r--tests/test_util_cache.lua309
-rw-r--r--tests/test_util_http.lua (renamed from tests/test_net_http.lua)22
-rw-r--r--tests/test_util_ip.lua89
-rw-r--r--tests/test_util_jid.lua74
-rw-r--r--tests/test_util_json.lua21
-rwxr-xr-xtests/test_util_json.sh39
-rw-r--r--tests/test_util_multitable.lua14
-rw-r--r--tests/test_util_queue.lua74
-rw-r--r--tests/test_util_random.lua10
-rw-r--r--tests/test_util_rfc3484.lua51
-rw-r--r--tests/test_util_rfc6724.lua97
-rw-r--r--tests/test_util_stanza.lua129
-rw-r--r--tests/test_util_throttle.lua26
-rw-r--r--tests/test_util_uuid.lua24
-rw-r--r--tests/test_util_xml.lua12
-rw-r--r--tests/test_util_xmppstream.lua83
-rw-r--r--tests/util/logger.lua7
63 files changed, 1240 insertions, 191 deletions
diff --git a/tests/json/fail1.json b/tests/json/fail1.json
new file mode 100644
index 00000000..6216b865
--- /dev/null
+++ b/tests/json/fail1.json
@@ -0,0 +1 @@
+"A JSON payload should be an object or array, not a string." \ No newline at end of file
diff --git a/tests/json/fail10.json b/tests/json/fail10.json
new file mode 100644
index 00000000..5d8c0047
--- /dev/null
+++ b/tests/json/fail10.json
@@ -0,0 +1 @@
+{"Extra value after close": true} "misplaced quoted value" \ No newline at end of file
diff --git a/tests/json/fail11.json b/tests/json/fail11.json
new file mode 100644
index 00000000..76eb95b4
--- /dev/null
+++ b/tests/json/fail11.json
@@ -0,0 +1 @@
+{"Illegal expression": 1 + 2} \ No newline at end of file
diff --git a/tests/json/fail12.json b/tests/json/fail12.json
new file mode 100644
index 00000000..77580a45
--- /dev/null
+++ b/tests/json/fail12.json
@@ -0,0 +1 @@
+{"Illegal invocation": alert()} \ No newline at end of file
diff --git a/tests/json/fail13.json b/tests/json/fail13.json
new file mode 100644
index 00000000..379406b5
--- /dev/null
+++ b/tests/json/fail13.json
@@ -0,0 +1 @@
+{"Numbers cannot have leading zeroes": 013} \ No newline at end of file
diff --git a/tests/json/fail14.json b/tests/json/fail14.json
new file mode 100644
index 00000000..0ed366b3
--- /dev/null
+++ b/tests/json/fail14.json
@@ -0,0 +1 @@
+{"Numbers cannot be hex": 0x14} \ No newline at end of file
diff --git a/tests/json/fail15.json b/tests/json/fail15.json
new file mode 100644
index 00000000..fc8376b6
--- /dev/null
+++ b/tests/json/fail15.json
@@ -0,0 +1 @@
+["Illegal backslash escape: \x15"] \ No newline at end of file
diff --git a/tests/json/fail16.json b/tests/json/fail16.json
new file mode 100644
index 00000000..3fe21d4b
--- /dev/null
+++ b/tests/json/fail16.json
@@ -0,0 +1 @@
+[\naked] \ No newline at end of file
diff --git a/tests/json/fail17.json b/tests/json/fail17.json
new file mode 100644
index 00000000..62b9214a
--- /dev/null
+++ b/tests/json/fail17.json
@@ -0,0 +1 @@
+["Illegal backslash escape: \017"] \ No newline at end of file
diff --git a/tests/json/fail18.json b/tests/json/fail18.json
new file mode 100644
index 00000000..edac9271
--- /dev/null
+++ b/tests/json/fail18.json
@@ -0,0 +1 @@
+[[[[[[[[[[[[[[[[[[[["Too deep"]]]]]]]]]]]]]]]]]]]] \ No newline at end of file
diff --git a/tests/json/fail19.json b/tests/json/fail19.json
new file mode 100644
index 00000000..3b9c46fa
--- /dev/null
+++ b/tests/json/fail19.json
@@ -0,0 +1 @@
+{"Missing colon" null} \ No newline at end of file
diff --git a/tests/json/fail2.json b/tests/json/fail2.json
new file mode 100644
index 00000000..6b7c11e5
--- /dev/null
+++ b/tests/json/fail2.json
@@ -0,0 +1 @@
+["Unclosed array" \ No newline at end of file
diff --git a/tests/json/fail20.json b/tests/json/fail20.json
new file mode 100644
index 00000000..27c1af3e
--- /dev/null
+++ b/tests/json/fail20.json
@@ -0,0 +1 @@
+{"Double colon":: null} \ No newline at end of file
diff --git a/tests/json/fail21.json b/tests/json/fail21.json
new file mode 100644
index 00000000..62474573
--- /dev/null
+++ b/tests/json/fail21.json
@@ -0,0 +1 @@
+{"Comma instead of colon", null} \ No newline at end of file
diff --git a/tests/json/fail22.json b/tests/json/fail22.json
new file mode 100644
index 00000000..a7752581
--- /dev/null
+++ b/tests/json/fail22.json
@@ -0,0 +1 @@
+["Colon instead of comma": false] \ No newline at end of file
diff --git a/tests/json/fail23.json b/tests/json/fail23.json
new file mode 100644
index 00000000..494add1c
--- /dev/null
+++ b/tests/json/fail23.json
@@ -0,0 +1 @@
+["Bad value", truth] \ No newline at end of file
diff --git a/tests/json/fail24.json b/tests/json/fail24.json
new file mode 100644
index 00000000..caff239b
--- /dev/null
+++ b/tests/json/fail24.json
@@ -0,0 +1 @@
+['single quote'] \ No newline at end of file
diff --git a/tests/json/fail25.json b/tests/json/fail25.json
new file mode 100644
index 00000000..8b7ad23e
--- /dev/null
+++ b/tests/json/fail25.json
@@ -0,0 +1 @@
+[" tab character in string "] \ No newline at end of file
diff --git a/tests/json/fail26.json b/tests/json/fail26.json
new file mode 100644
index 00000000..845d26a6
--- /dev/null
+++ b/tests/json/fail26.json
@@ -0,0 +1 @@
+["tab\ character\ in\ string\ "] \ No newline at end of file
diff --git a/tests/json/fail27.json b/tests/json/fail27.json
new file mode 100644
index 00000000..6b01a2ca
--- /dev/null
+++ b/tests/json/fail27.json
@@ -0,0 +1,2 @@
+["line
+break"] \ No newline at end of file
diff --git a/tests/json/fail28.json b/tests/json/fail28.json
new file mode 100644
index 00000000..621a0101
--- /dev/null
+++ b/tests/json/fail28.json
@@ -0,0 +1,2 @@
+["line\
+break"] \ No newline at end of file
diff --git a/tests/json/fail29.json b/tests/json/fail29.json
new file mode 100644
index 00000000..47ec421b
--- /dev/null
+++ b/tests/json/fail29.json
@@ -0,0 +1 @@
+[0e] \ No newline at end of file
diff --git a/tests/json/fail3.json b/tests/json/fail3.json
new file mode 100644
index 00000000..168c81eb
--- /dev/null
+++ b/tests/json/fail3.json
@@ -0,0 +1 @@
+{unquoted_key: "keys must be quoted"} \ No newline at end of file
diff --git a/tests/json/fail30.json b/tests/json/fail30.json
new file mode 100644
index 00000000..8ab0bc4b
--- /dev/null
+++ b/tests/json/fail30.json
@@ -0,0 +1 @@
+[0e+] \ No newline at end of file
diff --git a/tests/json/fail31.json b/tests/json/fail31.json
new file mode 100644
index 00000000..1cce602b
--- /dev/null
+++ b/tests/json/fail31.json
@@ -0,0 +1 @@
+[0e+-1] \ No newline at end of file
diff --git a/tests/json/fail32.json b/tests/json/fail32.json
new file mode 100644
index 00000000..45cba739
--- /dev/null
+++ b/tests/json/fail32.json
@@ -0,0 +1 @@
+{"Comma instead if closing brace": true, \ No newline at end of file
diff --git a/tests/json/fail33.json b/tests/json/fail33.json
new file mode 100644
index 00000000..ca5eb19d
--- /dev/null
+++ b/tests/json/fail33.json
@@ -0,0 +1 @@
+["mismatch"} \ No newline at end of file
diff --git a/tests/json/fail4.json b/tests/json/fail4.json
new file mode 100644
index 00000000..9de168bf
--- /dev/null
+++ b/tests/json/fail4.json
@@ -0,0 +1 @@
+["extra comma",] \ No newline at end of file
diff --git a/tests/json/fail5.json b/tests/json/fail5.json
new file mode 100644
index 00000000..ddf3ce3d
--- /dev/null
+++ b/tests/json/fail5.json
@@ -0,0 +1 @@
+["double extra comma",,] \ No newline at end of file
diff --git a/tests/json/fail6.json b/tests/json/fail6.json
new file mode 100644
index 00000000..ed91580e
--- /dev/null
+++ b/tests/json/fail6.json
@@ -0,0 +1 @@
+[ , "<-- missing value"] \ No newline at end of file
diff --git a/tests/json/fail7.json b/tests/json/fail7.json
new file mode 100644
index 00000000..8a96af3e
--- /dev/null
+++ b/tests/json/fail7.json
@@ -0,0 +1 @@
+["Comma after the close"], \ No newline at end of file
diff --git a/tests/json/fail8.json b/tests/json/fail8.json
new file mode 100644
index 00000000..b28479c6
--- /dev/null
+++ b/tests/json/fail8.json
@@ -0,0 +1 @@
+["Extra close"]] \ No newline at end of file
diff --git a/tests/json/fail9.json b/tests/json/fail9.json
new file mode 100644
index 00000000..5815574f
--- /dev/null
+++ b/tests/json/fail9.json
@@ -0,0 +1 @@
+{"Extra comma": true,} \ No newline at end of file
diff --git a/tests/json/pass1.json b/tests/json/pass1.json
new file mode 100644
index 00000000..70e26854
--- /dev/null
+++ b/tests/json/pass1.json
@@ -0,0 +1,58 @@
+[
+ "JSON Test Pattern pass1",
+ {"object with 1 member":["array with 1 element"]},
+ {},
+ [],
+ -42,
+ true,
+ false,
+ null,
+ {
+ "integer": 1234567890,
+ "real": -9876.543210,
+ "e": 0.123456789e-12,
+ "E": 1.234567890E+34,
+ "": 23456789012E66,
+ "zero": 0,
+ "one": 1,
+ "space": " ",
+ "quote": "\"",
+ "backslash": "\\",
+ "controls": "\b\f\n\r\t",
+ "slash": "/ & \/",
+ "alpha": "abcdefghijklmnopqrstuvwyz",
+ "ALPHA": "ABCDEFGHIJKLMNOPQRSTUVWYZ",
+ "digit": "0123456789",
+ "0123456789": "digit",
+ "special": "`1~!@#$%^&*()_+-={':[,]}|;.</>?",
+ "hex": "\u0123\u4567\u89AB\uCDEF\uabcd\uef4A",
+ "true": true,
+ "false": false,
+ "null": null,
+ "array":[ ],
+ "object":{ },
+ "address": "50 St. James Street",
+ "url": "http://www.JSON.org/",
+ "comment": "// /* <!-- --",
+ "# -- --> */": " ",
+ " s p a c e d " :[1,2 , 3
+
+,
+
+4 , 5 , 6 ,7 ],"compact":[1,2,3,4,5,6,7],
+ "jsontext": "{\"object with 1 member\":[\"array with 1 element\"]}",
+ "quotes": "&#34; \u0022 %22 0x22 034 &#x22;",
+ "\/\\\"\uCAFE\uBABE\uAB98\uFCDE\ubcda\uef4A\b\f\n\r\t`1~!@#$%^&*()_+-=[]{}|;:',./<>?"
+: "A key can be any string"
+ },
+ 0.5 ,98.6
+,
+99.44
+,
+
+1066,
+1e1,
+0.1e1,
+1e-1,
+1e00,2e+00,2e-00
+,"rosebud"] \ No newline at end of file
diff --git a/tests/json/pass2.json b/tests/json/pass2.json
new file mode 100644
index 00000000..d3c63c7a
--- /dev/null
+++ b/tests/json/pass2.json
@@ -0,0 +1 @@
+[[[[[[[[[[[[[[[[[[["Not too deep"]]]]]]]]]]]]]]]]]]] \ No newline at end of file
diff --git a/tests/json/pass3.json b/tests/json/pass3.json
new file mode 100644
index 00000000..4528d51f
--- /dev/null
+++ b/tests/json/pass3.json
@@ -0,0 +1,6 @@
+{
+ "JSON Test Pattern pass3": {
+ "The outermost value": "must be an object or array.",
+ "In this test": "It is an object."
+ }
+}
diff --git a/tests/modulemanager_option_conversion.lua b/tests/modulemanager_option_conversion.lua
index 7dceeaed..100dbe83 100644
--- a/tests/modulemanager_option_conversion.lua
+++ b/tests/modulemanager_option_conversion.lua
@@ -18,7 +18,7 @@ function test_value(value, returns)
assert(module:get_option_number("opt") == returns.number, "number doesn't match");
assert(module:get_option_string("opt") == returns.string, "string doesn't match");
assert(module:get_option_boolean("opt") == returns.boolean, "boolean doesn't match");
-
+
if type(returns.array) == "table" then
local target_array, returned_array = returns.array, module:get_option_array("opt");
assert(#target_array == #returned_array, "array length doesn't match");
@@ -28,7 +28,7 @@ function test_value(value, returns)
else
assert(module:get_option_array("opt") == returns.array, "array is returned (not nil)");
end
-
+
if type(returns.set) == "table" then
local target_items, returned_items = set.new(returns.set), module:get_option_set("opt");
assert(target_items == returned_items, "set doesn't match");
diff --git a/tests/run_tests.sh b/tests/run_tests.sh
index d93cd39b..7f1ee700 100755
--- a/tests/run_tests.sh
+++ b/tests/run_tests.sh
@@ -1,3 +1,3 @@
#!/bin/sh
rm reports/*.report
-lua test.lua $*
+exec lua test.lua "$@"
diff --git a/tests/test.lua b/tests/test.lua
index bb11ab26..bc33bb76 100644
--- a/tests/test.lua
+++ b/tests/test.lua
@@ -1,26 +1,35 @@
-- Prosody IM
-- Copyright (C) 2008-2010 Matthew Wild
-- Copyright (C) 2008-2010 Waqas Hussain
---
+--
-- This project is MIT/X11 licensed. Please see the
-- COPYING file in the source package for more information.
--
-
+local tests_passed = true;
function run_all_tests()
package.loaded["net.connlisteners"] = { get = function () return {} end };
dotest "util.jid"
dotest "util.multitable"
- dotest "util.rfc3484"
- dotest "net.http"
- dotest "core.modulemanager"
+ dotest "util.rfc6724"
+ dotest "util.http"
dotest "core.stanza_router"
dotest "core.s2smanager"
dotest "core.configmanager"
+ dotest "util.ip"
+ dotest "util.json"
dotest "util.stanza"
dotest "util.sasl.scram"
-
+ dotest "util.cache"
+ dotest "util.throttle"
+ dotest "util.uuid"
+ dotest "util.random"
+ dotest "util.xml"
+ dotest "util.xmppstream"
+ dotest "util.queue"
+ dotest "net.http.parser"
+
dosingletest("test_sasl.lua", "latin1toutf8");
dosingletest("test_utf8.lua", "valid");
end
@@ -39,6 +48,8 @@ local _realG = _G;
require "util.import"
+local envloadfile = require "util.envload".envloadfile;
+
local env_mt = { __index = function (t,k) return rawget(_realG, k) or print("WARNING: Attempt to access nil global '"..tostring(k).."'"); end };
function testlib_new_env(t)
return setmetatable(t or {}, env_mt);
@@ -76,29 +87,29 @@ function dosingletest(testname, fname)
local tests = setmetatable({}, { __index = _realG });
tests.__unit = testname;
tests.__test = fname;
- local chunk, err = loadfile(testname);
+ local chunk, err = envloadfile(testname, tests);
if not chunk then
print("WARNING: ", "Failed to load tests for "..testname, err);
return;
end
- setfenv(chunk, tests);
local success, err = pcall(chunk);
if not success then
print("WARNING: ", "Failed to initialise tests for "..testname, err);
return;
end
-
+
if type(tests[fname]) ~= "function" then
error(testname.." has no test '"..fname.."'", 0);
end
-
-
+
+
local line_hook, line_info = new_line_coverage_monitor(testname);
debug.sethook(line_hook, "l")
local success, ret = pcall(tests[fname]);
debug.sethook();
if not success then
+ tests_passed = false;
print("TEST FAILED! Unit: ["..testname.."] Function: ["..fname.."]");
print(" Location: "..ret:gsub(":%s*\n", "\n"));
line_info(fname, false, report_file);
@@ -115,13 +126,12 @@ function dotest(unitname)
_fakeG._G = _fakeG;
local tests = setmetatable({}, { __index = _fakeG });
tests.__unit = unitname;
- local chunk, err = loadfile("test_"..unitname:gsub("%.", "_")..".lua");
+ local chunk, err = envloadfile("test_"..unitname:gsub("%.", "_")..".lua", tests);
if not chunk then
print("WARNING: ", "Failed to load tests for "..unitname, err);
return;
end
- setfenv(chunk, tests);
local success, err = pcall(chunk);
if not success then
print("WARNING: ", "Failed to initialise tests for "..unitname, err);
@@ -130,25 +140,30 @@ function dotest(unitname)
if tests.env then setmetatable(tests.env, { __index = _realG }); end
local unit = setmetatable({}, { __index = setmetatable({ _G = tests.env or _fakeG }, { __index = tests.env or _fakeG }) });
local fn = "../"..unitname:gsub("%.", "/")..".lua";
- local chunk, err = loadfile(fn);
+ local chunk, err = envloadfile(fn, unit);
if not chunk then
print("WARNING: ", "Failed to load module: "..unitname, err);
return;
end
-
+
local oldmodule, old_M = _fakeG.module, _fakeG._M;
_fakeG.module = function ()
setmetatable(unit, nil);
unit._M = unit;
end
- setfenv(chunk, unit);
- local success, err = pcall(chunk);
+ local success, ret = pcall(chunk);
_fakeG.module, _fakeG._M = oldmodule, old_M;
if not success then
- print("WARNING: ", "Failed to initialise module: "..unitname, err);
+ print("WARNING: ", "Failed to initialise module: "..unitname, ret);
return;
end
-
+
+ if type(ret) == "table" then
+ for k,v in pairs(ret) do
+ unit[k] = v;
+ end
+ end
+
for name, f in pairs(unit) do
local test = rawget(tests, name);
if type(f) ~= "function" then
@@ -168,6 +183,7 @@ function dotest(unitname)
local success, ret = pcall(test, f, unit);
debug.sethook();
if not success then
+ tests_passed = false;
print("TEST FAILED! Unit: ["..unitname.."] Function: ["..name.."]");
print(" Location: "..ret:gsub(":%s*\n", "\n"));
line_info(name, false, report_file);
@@ -187,6 +203,7 @@ function runtest(f, msg)
if success and verbosity >= 2 then
print("SUBTEST PASSED: "..(msg or "(no description)"));
elseif (not success) and verbosity >= 0 then
+ tests_passed = false;
print("SUBTEST FAILED: "..(msg or "(no description)"));
error(ret, 0);
end
@@ -195,11 +212,11 @@ end
function new_line_coverage_monitor(file)
local lines_hit, funcs_hit = {}, {};
local total_lines, covered_lines = 0, 0;
-
+
for line in io.lines(file) do
total_lines = total_lines + 1;
end
-
+
return function (event, line) -- Line hook
if not lines_hit[line] then
local info = debug.getinfo(2, "fSL")
@@ -234,3 +251,5 @@ function new_line_coverage_monitor(file)
end
run_all_tests()
+
+os.exit(tests_passed and 0 or 1);
diff --git a/tests/test_core_configmanager.lua b/tests/test_core_configmanager.lua
index 132dfc74..5bd469c6 100644
--- a/tests/test_core_configmanager.lua
+++ b/tests/test_core_configmanager.lua
@@ -1,7 +1,7 @@
-- Prosody IM
-- Copyright (C) 2008-2010 Matthew Wild
-- Copyright (C) 2008-2010 Waqas Hussain
---
+--
-- This project is MIT/X11 licensed. Please see the
-- COPYING file in the source package for more information.
--
@@ -9,27 +9,23 @@
function get(get, config)
- config.set("example.com", "test", "testkey", 123);
- assert_equal(get("example.com", "test", "testkey"), 123, "Retrieving a set key");
-
- config.set("*", "test", "testkey1", 321);
- assert_equal(get("*", "test", "testkey1"), 321, "Retrieving a set global key");
- assert_equal(get("example.com", "test", "testkey1"), 321, "Retrieving a set key of undefined host, of which only a globally set one exists");
-
- config.set("example.com", "test", ""); -- Creates example.com host in config
- assert_equal(get("example.com", "test", "testkey1"), 321, "Retrieving a set key, of which only a globally set one exists");
-
+ config.set("example.com", "testkey", 123);
+ assert_equal(get("example.com", "testkey"), 123, "Retrieving a set key");
+
+ config.set("*", "testkey1", 321);
+ assert_equal(get("*", "testkey1"), 321, "Retrieving a set global key");
+ assert_equal(get("example.com", "testkey1"), 321, "Retrieving a set key of undefined host, of which only a globally set one exists");
+
+ config.set("example.com", ""); -- Creates example.com host in config
+ assert_equal(get("example.com", "testkey1"), 321, "Retrieving a set key, of which only a globally set one exists");
+
assert_equal(get(), nil, "No parameters to get()");
assert_equal(get("undefined host"), nil, "Getting for undefined host");
- assert_equal(get("undefined host", "undefined section"), nil, "Getting for undefined host & section");
- assert_equal(get("undefined host", "undefined section", "undefined key"), nil, "Getting for undefined host & section & key");
-
- assert_equal(get("example.com", "undefined section", "testkey"), nil, "Defined host, undefined section");
+ assert_equal(get("undefined host", "undefined key"), nil, "Getting for undefined host & key");
end
function set(set, u)
- assert_equal(set("*"), false, "Set with no section/key");
- assert_equal(set("*", "set_test"), false, "Set with no key");
+ assert_equal(set("*"), false, "Set with no key");
assert_equal(set("*", "set_test", "testkey"), true, "Setting a nil global value");
assert_equal(set("*", "set_test", "testkey", 123), true, "Setting a global value");
diff --git a/tests/test_core_modulemanager.lua b/tests/test_core_modulemanager.lua
deleted file mode 100644
index 9498875a..00000000
--- a/tests/test_core_modulemanager.lua
+++ /dev/null
@@ -1,48 +0,0 @@
--- Prosody IM
--- Copyright (C) 2008-2010 Matthew Wild
--- Copyright (C) 2008-2010 Waqas Hussain
---
--- This project is MIT/X11 licensed. Please see the
--- COPYING file in the source package for more information.
---
-
-local config = require "core.configmanager";
-local helpers = require "util.helpers";
-local set = require "util.set";
-
-function load_modules_for_host(load_modules_for_host, mm)
- local test_num = 0;
- local function test_load(global_modules_enabled, global_modules_disabled, host_modules_enabled, host_modules_disabled, expected_modules)
- test_num = test_num + 1;
- -- Prepare
- hosts = { ["example.com"] = {} };
- config.set("*", "core", "modules_enabled", global_modules_enabled);
- config.set("*", "core", "modules_disabled", global_modules_disabled);
- config.set("example.com", "core", "modules_enabled", host_modules_enabled);
- config.set("example.com", "core", "modules_disabled", host_modules_disabled);
-
- expected_modules = set.new(expected_modules);
- expected_modules:add_list(helpers.get_upvalue(load_modules_for_host, "autoload_modules"));
-
- local loaded_modules = set.new();
- function mm.load(host, module)
- assert_equal(host, "example.com", test_num..": Host isn't example.com but "..tostring(host));
- assert_equal(expected_modules:contains(module), true, test_num..": Loading unexpected module '"..tostring(module).."'");
- loaded_modules:add(module);
- end
- load_modules_for_host("example.com");
- assert_equal((expected_modules - loaded_modules):empty(), true, test_num..": Not all modules loaded: "..tostring(expected_modules - loaded_modules));
- end
-
- test_load({ "one", "two", "three" }, nil, nil, nil, { "one", "two", "three" });
- test_load({ "one", "two", "three" }, {}, nil, nil, { "one", "two", "three" });
- test_load({ "one", "two", "three" }, { "two" }, nil, nil, { "one", "three" });
- test_load({ "one", "two", "three" }, { "three" }, nil, nil, { "one", "two" });
- test_load({ "one", "two", "three" }, nil, nil, { "three" }, { "one", "two" });
- test_load({ "one", "two", "three" }, nil, { "three" }, { "three" }, { "one", "two", "three" });
-
- test_load({ "one", "two" }, nil, { "three" }, nil, { "one", "two", "three" });
- test_load({ "one", "two", "three" }, nil, { "three" }, nil, { "one", "two", "three" });
- test_load({ "one", "two", "three" }, { "three" }, { "three" }, nil, { "one", "two", "three" });
- test_load({ "one", "two" }, { "three" }, { "three" }, nil, { "one", "two", "three" });
-end
diff --git a/tests/test_core_s2smanager.lua b/tests/test_core_s2smanager.lua
index b49c7da6..d2dbf830 100644
--- a/tests/test_core_s2smanager.lua
+++ b/tests/test_core_s2smanager.lua
@@ -1,11 +1,14 @@
-- Prosody IM
-- Copyright (C) 2008-2010 Matthew Wild
-- Copyright (C) 2008-2010 Waqas Hussain
---
+--
-- This project is MIT/X11 licensed. Please see the
-- COPYING file in the source package for more information.
--
+env = {
+ prosody = { events = require "util.events".new() };
+};
function compare_srv_priorities(csp)
local r1 = { priority = 10, weight = 0 }
@@ -13,7 +16,7 @@ function compare_srv_priorities(csp)
local r3 = { priority = 1000, weight = 2 }
local r4 = { priority = 1000, weight = 2 }
local r5 = { priority = 1000, weight = 5 }
-
+
assert_equal(csp(r1, r1), false);
assert_equal(csp(r1, r2), true);
assert_equal(csp(r1, r3), true);
diff --git a/tests/test_core_stanza_router.lua b/tests/test_core_stanza_router.lua
index 0a93694f..ca6b78fc 100644
--- a/tests/test_core_stanza_router.lua
+++ b/tests/test_core_stanza_router.lua
@@ -1,7 +1,7 @@
-- Prosody IM
-- Copyright (C) 2008-2010 Matthew Wild
-- Copyright (C) 2008-2010 Waqas Hussain
---
+--
-- This project is MIT/X11 licensed. Please see the
-- COPYING file in the source package for more information.
--
@@ -14,7 +14,7 @@ function core_process_stanza(core_process_stanza, u)
local s2sin_session = { from_host = "remotehost", to_host = "localhost", type = "s2sin", hosts = { ["remotehost"] = { authed = true } } }
local local_host_session = { host = "localhost", type = "local", s2sout = { ["remotehost"] = s2sout_session } }
local local_user_session = { username = "user", host = "localhost", resource = "resource", full_jid = "user@localhost/resource", type = "c2s" }
-
+
_G.prosody.hosts["localhost"] = local_host_session;
_G.prosody.full_sessions["user@localhost/resource"] = local_user_session;
_G.prosody.bare_sessions["user@localhost"] = { sessions = { resource = local_user_session } };
@@ -23,15 +23,15 @@ function core_process_stanza(core_process_stanza, u)
local function test_message_full_jid()
local env = testlib_new_env();
local msg = stanza.stanza("message", { to = "user@localhost/resource", type = "chat" }):tag("body"):text("Hello world");
-
+
local target_routed;
-
+
function env.core_post_stanza(p_origin, p_stanza)
assert_equal(p_origin, local_user_session, "origin of routed stanza is not correct");
assert_equal(p_stanza, msg, "routed stanza is not correct one: "..p_stanza:pretty_print());
target_routed = true;
end
-
+
env.hosts = hosts;
env.prosody = { hosts = hosts };
setfenv(core_process_stanza, env);
@@ -42,9 +42,9 @@ function core_process_stanza(core_process_stanza, u)
local function test_message_bare_jid()
local env = testlib_new_env();
local msg = stanza.stanza("message", { to = "user@localhost", type = "chat" }):tag("body"):text("Hello world");
-
+
local target_routed;
-
+
function env.core_post_stanza(p_origin, p_stanza)
assert_equal(p_origin, local_user_session, "origin of routed stanza is not correct");
assert_equal(p_stanza, msg, "routed stanza is not correct one: "..p_stanza:pretty_print());
@@ -60,9 +60,9 @@ function core_process_stanza(core_process_stanza, u)
local function test_message_no_to()
local env = testlib_new_env();
local msg = stanza.stanza("message", { type = "chat" }):tag("body"):text("Hello world");
-
+
local target_handled;
-
+
function env.core_post_stanza(p_origin, p_stanza)
assert_equal(p_origin, local_user_session, "origin of handled stanza is not correct");
assert_equal(p_stanza, msg, "handled stanza is not correct one: "..p_stanza:pretty_print());
@@ -78,9 +78,9 @@ function core_process_stanza(core_process_stanza, u)
local function test_message_to_remote_bare()
local env = testlib_new_env();
local msg = stanza.stanza("message", { to = "user@remotehost", type = "chat" }):tag("body"):text("Hello world");
-
+
local target_routed;
-
+
function env.core_route_stanza(p_origin, p_stanza)
assert_equal(p_origin, local_user_session, "origin of handled stanza is not correct");
assert_equal(p_stanza, msg, "handled stanza is not correct one: "..p_stanza:pretty_print());
@@ -88,7 +88,7 @@ function core_process_stanza(core_process_stanza, u)
end
function env.core_post_stanza(...) env.core_route_stanza(...); end
-
+
env.hosts = hosts;
setfenv(core_process_stanza, env);
assert_equal(core_process_stanza(local_user_session, msg), nil, "core_process_stanza returned incorrect value");
@@ -98,9 +98,9 @@ function core_process_stanza(core_process_stanza, u)
local function test_message_to_remote_server()
local env = testlib_new_env();
local msg = stanza.stanza("message", { to = "remotehost", type = "chat" }):tag("body"):text("Hello world");
-
+
local target_routed;
-
+
function env.core_route_stanza(p_origin, p_stanza)
assert_equal(p_origin, local_user_session, "origin of handled stanza is not correct");
assert_equal(p_stanza, msg, "handled stanza is not correct one: "..p_stanza:pretty_print());
@@ -123,9 +123,9 @@ function core_process_stanza(core_process_stanza, u)
local function test_iq_to_remote_server()
local env = testlib_new_env();
local msg = stanza.stanza("iq", { to = "remotehost", type = "get", id = "id" }):tag("body"):text("Hello world");
-
+
local target_routed;
-
+
function env.core_route_stanza(p_origin, p_stanza)
assert_equal(p_origin, local_user_session, "origin of handled stanza is not correct");
assert_equal(p_stanza, msg, "handled stanza is not correct one: "..p_stanza:pretty_print());
@@ -145,9 +145,9 @@ function core_process_stanza(core_process_stanza, u)
local function test_iq_error_to_local_user()
local env = testlib_new_env();
local msg = stanza.stanza("iq", { to = "user@localhost/resource", from = "user@remotehost", type = "error", id = "id" }):tag("error", { type = 'cancel' }):tag("item-not-found", { xmlns='urn:ietf:params:xml:ns:xmpp-stanzas' });
-
+
local target_routed;
-
+
function env.core_route_stanza(p_origin, p_stanza)
assert_equal(p_origin, s2sin_session, "origin of handled stanza is not correct");
assert_equal(p_stanza, msg, "handled stanza is not correct one: "..p_stanza:pretty_print());
@@ -167,9 +167,9 @@ function core_process_stanza(core_process_stanza, u)
local function test_iq_to_local_bare()
local env = testlib_new_env();
local msg = stanza.stanza("iq", { to = "user@localhost", from = "user@localhost", type = "get", id = "id" }):tag("ping", { xmlns = "urn:xmpp:ping:0" });
-
+
local target_handled;
-
+
function env.core_post_stanza(p_origin, p_stanza)
assert_equal(p_origin, local_user_session, "origin of handled stanza is not correct");
assert_equal(p_stanza, msg, "handled stanza is not correct one: "..p_stanza:pretty_print());
@@ -209,11 +209,11 @@ function core_route_stanza(core_route_stanza)
local msg2 = stanza.stanza("iq", { to = "user@localhost/foo", from = "user@localhost", type = "error" }):tag("ping", { xmlns = "urn:xmpp:ping:0" });
--package.loaded["core.usermanager"] = { user_exists = function (user, host) print("RAR!") return true or user == "user" and host == "localhost" and true; end };
local target_handled, target_replied;
-
+
function env.core_post_stanza(p_origin, p_stanza)
target_handled = true;
end
-
+
function local_user_session.send(data)
--print("Replying with: ", tostring(data));
--print(debug.traceback())
diff --git a/tests/test_net_http_parser.lua b/tests/test_net_http_parser.lua
new file mode 100644
index 00000000..1157b5ac
--- /dev/null
+++ b/tests/test_net_http_parser.lua
@@ -0,0 +1,47 @@
+local httpstreams = { [[
+GET / HTTP/1.1
+Host: example.com
+
+]], [[
+HTTP/1.1 200 OK
+Content-Length: 0
+
+]], [[
+HTTP/1.1 200 OK
+Content-Length: 7
+
+Hello
+HTTP/1.1 200 OK
+Transfer-Encoding: chunked
+
+1
+H
+1
+e
+2
+ll
+1
+o
+0
+
+
+]]
+}
+
+function new(new)
+
+ for _, stream in ipairs(httpstreams) do
+ local success;
+ local function success_cb(packet)
+ success = true;
+ end
+ stream = stream:gsub("\n", "\r\n");
+ local parser = new(success_cb, error, stream:sub(1,4) == "HTTP" and "client" or "server")
+ for chunk in stream:gmatch("..?.?") do
+ parser:feed(chunk);
+ end
+
+ assert_is(success);
+ end
+
+end
diff --git a/tests/test_sasl.lua b/tests/test_sasl.lua
index 271fa69a..dd63c5a0 100644
--- a/tests/test_sasl.lua
+++ b/tests/test_sasl.lua
@@ -1,7 +1,7 @@
-- Prosody IM
-- Copyright (C) 2008-2010 Matthew Wild
-- Copyright (C) 2008-2010 Waqas Hussain
---
+--
-- This project is MIT/X11 licensed. Please see the
-- COPYING file in the source package for more information.
--
@@ -30,7 +30,7 @@ function latin1toutf8()
local function assert_utf8(latin, utf8)
assert_equal(_latin1toutf8(latin), utf8, "Incorrect UTF8 from Latin1: "..tostring(latin));
end
-
+
assert_utf8("", "")
assert_utf8("test", "test")
assert_utf8(nil, nil)
diff --git a/tests/test_utf8.lua b/tests/test_utf8.lua
index 481eff5d..48859960 100644
--- a/tests/test_utf8.lua
+++ b/tests/test_utf8.lua
@@ -4,14 +4,13 @@ package.path = "../?.lua";
function valid()
local encodings = require "util.encodings";
local utf8 = assert(encodings.utf8, "no encodings.utf8 module");
-
+
for line in io.lines("utf8_sequences.txt") do
local data = line:match(":%s*([^#]+)"):gsub("%s+", ""):gsub("..", function (c) return string.char(tonumber(c, 16)); end)
local expect = line:match("(%S+):");
if expect ~= "pass" and expect ~= "fail" then
error("unknown expectation: "..line:match("^[^:]+"));
end
- local prefix, style = " ", valid_style;
local valid = utf8.valid(data);
assert_equal(valid, utf8.valid(data.." "));
assert_equal(valid, expect == "pass", line);
diff --git a/tests/test_util_cache.lua b/tests/test_util_cache.lua
new file mode 100644
index 00000000..4240c433
--- /dev/null
+++ b/tests/test_util_cache.lua
@@ -0,0 +1,309 @@
+function new(new)
+ local c = new(5);
+
+ local function expect_kv(key, value, actual_key, actual_value)
+ assert_equal(key, actual_key, "key incorrect");
+ assert_equal(value, actual_value, "value incorrect");
+ end
+
+ expect_kv(nil, nil, c:head());
+ expect_kv(nil, nil, c:tail());
+
+ assert_equal(c:count(), 0);
+
+ c:set("one", 1)
+ assert_equal(c:count(), 1);
+ expect_kv("one", 1, c:head());
+ expect_kv("one", 1, c:tail());
+
+ c:set("two", 2)
+ expect_kv("two", 2, c:head());
+ expect_kv("one", 1, c:tail());
+
+ c:set("three", 3)
+ expect_kv("three", 3, c:head());
+ expect_kv("one", 1, c:tail());
+
+ c:set("four", 4)
+ c:set("five", 5);
+ assert_equal(c:count(), 5);
+ expect_kv("five", 5, c:head());
+ expect_kv("one", 1, c:tail());
+
+ c:set("foo", nil);
+ assert_equal(c:count(), 5);
+ expect_kv("five", 5, c:head());
+ expect_kv("one", 1, c:tail());
+
+ assert_equal(c:get("one"), 1);
+ expect_kv("five", 5, c:head());
+ expect_kv("one", 1, c:tail());
+
+ assert_equal(c:get("two"), 2);
+ assert_equal(c:get("three"), 3);
+ assert_equal(c:get("four"), 4);
+ assert_equal(c:get("five"), 5);
+
+ assert_equal(c:get("foo"), nil);
+ assert_equal(c:get("bar"), nil);
+
+ c:set("six", 6);
+ assert_equal(c:count(), 5);
+ expect_kv("six", 6, c:head());
+ expect_kv("two", 2, c:tail());
+
+ assert_equal(c:get("one"), nil);
+ assert_equal(c:get("two"), 2);
+ assert_equal(c:get("three"), 3);
+ assert_equal(c:get("four"), 4);
+ assert_equal(c:get("five"), 5);
+ assert_equal(c:get("six"), 6);
+
+ c:set("three", nil);
+ assert_equal(c:count(), 4);
+
+ assert_equal(c:get("one"), nil);
+ assert_equal(c:get("two"), 2);
+ assert_equal(c:get("three"), nil);
+ assert_equal(c:get("four"), 4);
+ assert_equal(c:get("five"), 5);
+ assert_equal(c:get("six"), 6);
+
+ c:set("seven", 7);
+ assert_equal(c:count(), 5);
+
+ assert_equal(c:get("one"), nil);
+ assert_equal(c:get("two"), 2);
+ assert_equal(c:get("three"), nil);
+ assert_equal(c:get("four"), 4);
+ assert_equal(c:get("five"), 5);
+ assert_equal(c:get("six"), 6);
+ assert_equal(c:get("seven"), 7);
+
+ c:set("eight", 8);
+ assert_equal(c:count(), 5);
+
+ assert_equal(c:get("one"), nil);
+ assert_equal(c:get("two"), nil);
+ assert_equal(c:get("three"), nil);
+ assert_equal(c:get("four"), 4);
+ assert_equal(c:get("five"), 5);
+ assert_equal(c:get("six"), 6);
+ assert_equal(c:get("seven"), 7);
+ assert_equal(c:get("eight"), 8);
+
+ c:set("four", 4);
+ assert_equal(c:count(), 5);
+
+ assert_equal(c:get("one"), nil);
+ assert_equal(c:get("two"), nil);
+ assert_equal(c:get("three"), nil);
+ assert_equal(c:get("four"), 4);
+ assert_equal(c:get("five"), 5);
+ assert_equal(c:get("six"), 6);
+ assert_equal(c:get("seven"), 7);
+ assert_equal(c:get("eight"), 8);
+
+ c:set("nine", 9);
+ assert_equal(c:count(), 5);
+
+ assert_equal(c:get("one"), nil);
+ assert_equal(c:get("two"), nil);
+ assert_equal(c:get("three"), nil);
+ assert_equal(c:get("four"), 4);
+ assert_equal(c:get("five"), nil);
+ assert_equal(c:get("six"), 6);
+ assert_equal(c:get("seven"), 7);
+ assert_equal(c:get("eight"), 8);
+ assert_equal(c:get("nine"), 9);
+
+ do
+ local keys = { "nine", "four", "eight", "seven", "six" };
+ local values = { 9, 4, 8, 7, 6 };
+ local i = 0;
+ for k, v in c:items() do
+ i = i + 1;
+ assert_equal(k, keys[i]);
+ assert_equal(v, values[i]);
+ end
+ assert_equal(i, 5);
+
+ c:set("four", "2+2");
+ assert_equal(c:count(), 5);
+
+ assert_equal(c:get("one"), nil);
+ assert_equal(c:get("two"), nil);
+ assert_equal(c:get("three"), nil);
+ assert_equal(c:get("four"), "2+2");
+ assert_equal(c:get("five"), nil);
+ assert_equal(c:get("six"), 6);
+ assert_equal(c:get("seven"), 7);
+ assert_equal(c:get("eight"), 8);
+ assert_equal(c:get("nine"), 9);
+ end
+
+ do
+ local keys = { "four", "nine", "eight", "seven", "six" };
+ local values = { "2+2", 9, 8, 7, 6 };
+ local i = 0;
+ for k, v in c:items() do
+ i = i + 1;
+ assert_equal(k, keys[i]);
+ assert_equal(v, values[i]);
+ end
+ assert_equal(i, 5);
+
+ c:set("foo", nil);
+ assert_equal(c:count(), 5);
+
+ assert_equal(c:get("one"), nil);
+ assert_equal(c:get("two"), nil);
+ assert_equal(c:get("three"), nil);
+ assert_equal(c:get("four"), "2+2");
+ assert_equal(c:get("five"), nil);
+ assert_equal(c:get("six"), 6);
+ assert_equal(c:get("seven"), 7);
+ assert_equal(c:get("eight"), 8);
+ assert_equal(c:get("nine"), 9);
+ end
+
+ do
+ local keys = { "four", "nine", "eight", "seven", "six" };
+ local values = { "2+2", 9, 8, 7, 6 };
+ local i = 0;
+ for k, v in c:items() do
+ i = i + 1;
+ assert_equal(k, keys[i]);
+ assert_equal(v, values[i]);
+ end
+ assert_equal(i, 5);
+
+ c:set("four", nil);
+
+ assert_equal(c:get("one"), nil);
+ assert_equal(c:get("two"), nil);
+ assert_equal(c:get("three"), nil);
+ assert_equal(c:get("four"), nil);
+ assert_equal(c:get("five"), nil);
+ assert_equal(c:get("six"), 6);
+ assert_equal(c:get("seven"), 7);
+ assert_equal(c:get("eight"), 8);
+ assert_equal(c:get("nine"), 9);
+ end
+
+ do
+ local keys = { "nine", "eight", "seven", "six" };
+ local values = { 9, 8, 7, 6 };
+ local i = 0;
+ for k, v in c:items() do
+ i = i + 1;
+ assert_equal(k, keys[i]);
+ assert_equal(v, values[i]);
+ end
+ assert_equal(i, 4);
+ end
+
+ do
+ local evicted_key, evicted_value;
+ local c2 = new(3, function (_key, _value)
+ evicted_key, evicted_value = _key, _value;
+ end);
+ local function set(k, v, should_evict_key, should_evict_value)
+ evicted_key, evicted_value = nil, nil;
+ c2:set(k, v);
+ assert_equal(evicted_key, should_evict_key);
+ assert_equal(evicted_value, should_evict_value);
+ end
+ set("a", 1)
+ set("a", 1)
+ set("a", 1)
+ set("a", 1)
+ set("a", 1)
+
+ set("b", 2)
+ set("c", 3)
+ set("b", 2)
+ set("d", 4, "a", 1)
+ set("e", 5, "c", 3)
+ end
+
+ do
+ local evicted_key, evicted_value;
+ local c3 = new(1, function (_key, _value)
+ evicted_key, evicted_value = _key, _value;
+ if _key == "a" then
+ -- Sanity check for what we're evicting
+ assert_equal(_key, "a");
+ assert_equal(_value, 1);
+ -- We're going to block eviction of this key/value, so set to nil...
+ evicted_key, evicted_value = nil, nil;
+ -- Returning false to block eviction
+ return false
+ end
+ end);
+ local function set(k, v, should_evict_key, should_evict_value)
+ evicted_key, evicted_value = nil, nil;
+ local ret = c3:set(k, v);
+ assert_equal(evicted_key, should_evict_key);
+ assert_equal(evicted_value, should_evict_value);
+ return ret;
+ end
+ set("a", 1)
+ set("a", 1)
+ set("a", 1)
+ set("a", 1)
+ set("a", 1)
+
+ -- Our on_evict prevents "a" from being evicted, causing this to fail...
+ assert_equal(set("b", 2), false, "Failed to prevent eviction, or signal result");
+
+ expect_kv("a", 1, c3:head());
+ expect_kv("a", 1, c3:tail());
+
+ -- Check the final state is what we expect
+ assert_equal(c3:get("a"), 1);
+ assert_equal(c3:get("b"), nil);
+ assert_equal(c3:count(), 1);
+ end
+
+
+ local c4 = new(3, false);
+
+ assert_equal(c4:set("a", 1), true);
+ assert_equal(c4:set("a", 1), true);
+ assert_equal(c4:set("a", 1), true);
+ assert_equal(c4:set("a", 1), true);
+ assert_equal(c4:set("b", 2), true);
+ assert_equal(c4:set("c", 3), true);
+ assert_equal(c4:set("d", 4), false);
+ assert_equal(c4:set("d", 4), false);
+ assert_equal(c4:set("d", 4), false);
+
+ expect_kv("c", 3, c4:head());
+ expect_kv("a", 1, c4:tail());
+
+ local c5 = new(3, function (k, v)
+ if k == "a" then
+ return nil;
+ elseif k == "b" then
+ return true;
+ end
+ return false;
+ end);
+
+ assert_equal(c5:set("a", 1), true);
+ assert_equal(c5:set("a", 1), true);
+ assert_equal(c5:set("a", 1), true);
+ assert_equal(c5:set("a", 1), true);
+ assert_equal(c5:set("b", 2), true);
+ assert_equal(c5:set("c", 3), true);
+ assert_equal(c5:set("d", 4), true); -- "a" evicted (cb returned nil)
+ assert_equal(c5:set("d", 4), true); -- nop
+ assert_equal(c5:set("d", 4), true); -- nop
+ assert_equal(c5:set("e", 5), true); -- "b" evicted (cb returned true)
+ assert_equal(c5:set("f", 6), false); -- "c" won't evict (cb returned false)
+
+ expect_kv("e", 5, c5:head());
+ expect_kv("c", 3, c5:tail());
+
+end
diff --git a/tests/test_net_http.lua b/tests/test_util_http.lua
index e68f96e9..d9cc2779 100644
--- a/tests/test_net_http.lua
+++ b/tests/test_util_http.lua
@@ -1,7 +1,7 @@
-- Prosody IM
-- Copyright (C) 2008-2010 Matthew Wild
-- Copyright (C) 2008-2010 Waqas Hussain
---
+--
-- This project is MIT/X11 licensed. Please see the
-- COPYING file in the source package for more information.
--
@@ -25,13 +25,17 @@ function formencode(formencode)
end
function formdecode(formdecode)
- local t = formdecode("one=1&two=2");
- assert_table(t[1]);
- assert_equal(t[1].name, "one"); assert_equal(t[1].value, "1");
- assert_table(t[2]);
- assert_equal(t[2].name, "two"); assert_equal(t[2].value, "2");
+ do
+ local t = formdecode("one=1&two=2");
+ assert_table(t[1]);
+ assert_equal(t[1].name, "one"); assert_equal(t[1].value, "1");
+ assert_table(t[2]);
+ assert_equal(t[2].name, "two"); assert_equal(t[2].value, "2");
+ end
- local t = formdecode("one+two=1&two+one%26=2");
- assert_equal(t[1].name, "one two"); assert_equal(t[1].value, "1");
- assert_equal(t[2].name, "two one&"); assert_equal(t[2].value, "2");
+ do
+ local t = formdecode("one+two=1&two+one%26=2");
+ assert_equal(t[1].name, "one two"); assert_equal(t[1].value, "1");
+ assert_equal(t[2].name, "two one&"); assert_equal(t[2].value, "2");
+ end
end
diff --git a/tests/test_util_ip.lua b/tests/test_util_ip.lua
new file mode 100644
index 00000000..0ded1123
--- /dev/null
+++ b/tests/test_util_ip.lua
@@ -0,0 +1,89 @@
+
+function match(match, _M)
+ local _ = _M.new_ip;
+ local ip = _"10.20.30.40";
+ assert_equal(match(ip, _"10.0.0.0", 8), true);
+ assert_equal(match(ip, _"10.0.0.0", 16), false);
+ assert_equal(match(ip, _"10.0.0.0", 24), false);
+ assert_equal(match(ip, _"10.0.0.0", 32), false);
+
+ assert_equal(match(ip, _"10.20.0.0", 8), true);
+ assert_equal(match(ip, _"10.20.0.0", 16), true);
+ assert_equal(match(ip, _"10.20.0.0", 24), false);
+ assert_equal(match(ip, _"10.20.0.0", 32), false);
+
+ assert_equal(match(ip, _"0.0.0.0", 32), false);
+ assert_equal(match(ip, _"0.0.0.0", 0), true);
+ assert_equal(match(ip, _"0.0.0.0"), false);
+
+ assert_equal(match(ip, _"10.0.0.0", 255), false, "excessive number of bits");
+ assert_equal(match(ip, _"10.0.0.0", -8), true, "negative number of bits");
+ assert_equal(match(ip, _"10.0.0.0", -32), true, "negative number of bits");
+ assert_equal(match(ip, _"10.0.0.0", 0), true, "zero bits");
+ assert_equal(match(ip, _"10.0.0.0"), false, "no specified number of bits (differing ip)");
+ assert_equal(match(ip, _"10.20.30.40"), true, "no specified number of bits (same ip)");
+
+ assert_equal(match(_"127.0.0.1", _"127.0.0.1"), true, "simple ip");
+
+ assert_equal(match(_"8.8.8.8", _"8.8.0.0", 16), true);
+ assert_equal(match(_"8.8.4.4", _"8.8.0.0", 16), true);
+end
+
+function parse_cidr(parse_cidr, _M)
+ local new_ip = _M.new_ip;
+
+ assert_equal(new_ip"0.0.0.0", new_ip"0.0.0.0")
+
+ local function assert_cidr(cidr, ip, bits)
+ local parsed_ip, parsed_bits = parse_cidr(cidr);
+ assert_equal(new_ip(ip), parsed_ip, cidr.." parsed ip is "..ip);
+ assert_equal(bits, parsed_bits, cidr.." parsed bits is "..tostring(bits));
+ end
+ assert_cidr("0.0.0.0", "0.0.0.0", nil);
+ assert_cidr("127.0.0.1", "127.0.0.1", nil);
+ assert_cidr("127.0.0.1/0", "127.0.0.1", 0);
+ assert_cidr("127.0.0.1/8", "127.0.0.1", 8);
+ assert_cidr("127.0.0.1/32", "127.0.0.1", 32);
+ assert_cidr("127.0.0.1/256", "127.0.0.1", 256);
+ assert_cidr("::/48", "::", 48);
+end
+
+function new_ip(new_ip)
+ local v4, v6 = "IPv4", "IPv6";
+ local function assert_proto(s, proto)
+ local ip = new_ip(s);
+ if proto then
+ assert_equal(ip and ip.proto, proto, "protocol is correct for "..("%q"):format(s));
+ else
+ assert_equal(ip, nil, "address is invalid");
+ end
+ end
+ assert_proto("127.0.0.1", v4);
+ assert_proto("::1", v6);
+ assert_proto("", nil);
+ assert_proto("abc", nil);
+ assert_proto(" ", nil);
+end
+
+function commonPrefixLength(cpl, _M)
+ local new_ip = _M.new_ip;
+ local function assert_cpl6(a, b, len, v4)
+ local ipa, ipb = new_ip(a), new_ip(b);
+ if v4 then len = len+96; end
+ assert_equal(cpl(ipa, ipb), len, "common prefix length of "..a.." and "..b.." is "..len);
+ assert_equal(cpl(ipb, ipa), len, "common prefix length of "..b.." and "..a.." is "..len);
+ end
+ local function assert_cpl4(a, b, len)
+ return assert_cpl6(a, b, len, "IPv4");
+ end
+ assert_cpl4("0.0.0.0", "0.0.0.0", 32);
+ assert_cpl4("255.255.255.255", "0.0.0.0", 0);
+ assert_cpl4("255.255.255.255", "255.255.0.0", 16);
+ assert_cpl4("255.255.255.255", "255.255.255.255", 32);
+ assert_cpl4("255.255.255.255", "255.255.255.255", 32);
+
+ assert_cpl6("::1", "::1", 128);
+ assert_cpl6("abcd::1", "abcd::1", 128);
+ assert_cpl6("abcd::abcd", "abcd::", 112);
+ assert_cpl6("abcd::abcd", "abcd::abcd:abcd", 96);
+end
diff --git a/tests/test_util_jid.lua b/tests/test_util_jid.lua
index a817e644..0ac5827e 100644
--- a/tests/test_util_jid.lua
+++ b/tests/test_util_jid.lua
@@ -1,7 +1,7 @@
-- Prosody IM
-- Copyright (C) 2008-2010 Matthew Wild
-- Copyright (C) 2008-2010 Waqas Hussain
---
+--
-- This project is MIT/X11 licensed. Please see the
-- COPYING file in the source package for more information.
--
@@ -19,7 +19,7 @@ end
function split(split)
- function test(input_jid, expected_node, expected_server, expected_resource)
+ local function test(input_jid, expected_node, expected_server, expected_resource)
local rnode, rserver, rresource = split(input_jid);
assert_equal(expected_node, rnode, "split("..tostring(input_jid)..") failed");
assert_equal(expected_server, rserver, "split("..tostring(input_jid)..") failed");
@@ -71,3 +71,73 @@ function compare(compare)
assert_equal(compare("user@other-host", "host"), false, "host should not match");
assert_equal(compare("user@other-host", "user@host"), false, "host should not match");
end
+
+function node(node)
+ local function test(jid, expected_node)
+ assert_equal(node(jid), expected_node, "Unexpected node for "..tostring(jid));
+ end
+
+ test("example.com", nil);
+ test("foo.example.com", nil);
+ test("foo.example.com/resource", nil);
+ test("foo.example.com/some resource", nil);
+ test("foo.example.com/some@resource", nil);
+
+ test("foo@foo.example.com/some@resource", "foo");
+ test("foo@example/some@resource", "foo");
+
+ test("foo@example/@resource", "foo");
+ test("foo@example@resource", nil);
+ test("foo@example", "foo");
+ test("foo", nil);
+
+ test(nil, nil);
+end
+
+function host(host)
+ local function test(jid, expected_host)
+ assert_equal(host(jid), expected_host, "Unexpected host for "..tostring(jid));
+ end
+
+ test("example.com", "example.com");
+ test("foo.example.com", "foo.example.com");
+ test("foo.example.com/resource", "foo.example.com");
+ test("foo.example.com/some resource", "foo.example.com");
+ test("foo.example.com/some@resource", "foo.example.com");
+
+ test("foo@foo.example.com/some@resource", "foo.example.com");
+ test("foo@example/some@resource", "example");
+
+ test("foo@example/@resource", "example");
+ test("foo@example@resource", nil);
+ test("foo@example", "example");
+ test("foo", "foo");
+
+ test(nil, nil);
+end
+
+function resource(resource)
+ local function test(jid, expected_resource)
+ assert_equal(resource(jid), expected_resource, "Unexpected resource for "..tostring(jid));
+ end
+
+ test("example.com", nil);
+ test("foo.example.com", nil);
+ test("foo.example.com/resource", "resource");
+ test("foo.example.com/some resource", "some resource");
+ test("foo.example.com/some@resource", "some@resource");
+
+ test("foo@foo.example.com/some@resource", "some@resource");
+ test("foo@example/some@resource", "some@resource");
+
+ test("foo@example/@resource", "@resource");
+ test("foo@example@resource", nil);
+ test("foo@example", nil);
+ test("foo", nil);
+ test("/foo", nil);
+ test("@x/foo", nil);
+ test("@/foo", nil);
+
+ test(nil, nil);
+end
+
diff --git a/tests/test_util_json.lua b/tests/test_util_json.lua
new file mode 100644
index 00000000..2c1a9ce9
--- /dev/null
+++ b/tests/test_util_json.lua
@@ -0,0 +1,21 @@
+
+function encode(encode, json)
+ local function test(f, j, e)
+ if e then
+ assert_equal(f(j), e);
+ end
+ assert_equal(f(j), f(json.decode(f(j))));
+ end
+ test(encode, json.null, "null")
+ test(encode, {}, "{}")
+ test(encode, {a=1});
+ test(encode, {a={1,2,3}});
+ test(encode, {1}, "[1]");
+end
+
+function decode(decode)
+ local empty_array = decode("[]");
+ assert_equal(type(empty_array), "table");
+ assert_equal(#empty_array, 0);
+ assert_equal(next(empty_array), nil);
+end
diff --git a/tests/test_util_json.sh b/tests/test_util_json.sh
new file mode 100755
index 00000000..bbbd132b
--- /dev/null
+++ b/tests/test_util_json.sh
@@ -0,0 +1,39 @@
+#!/bin/bash
+
+export LUA_PATH="../?.lua;;"
+export LUA_CPATH="../?.so;;"
+
+#set -x
+
+if ! which "$RUNWITH"; then
+ echo "Unable to find interpreter $RUNWITH";
+ exit 1;
+fi
+
+if ! $RUNWITH -e 'assert(require"util.json")' 2>/dev/null; then
+ echo "Unable to find util.json";
+ exit 1;
+fi
+
+FAIL=0
+
+for f in json/pass*.json; do
+ if ! $RUNWITH -e 'local j=require"util.json" assert(j.decode(io.read("*a"))~=nil)' <"$f" 2>/dev/null; then
+ echo "Failed to decode valid JSON: $f";
+ FAIL=1
+ fi
+done
+
+for f in json/fail*.json; do
+ if ! $RUNWITH -e 'local j=require"util.json" assert(j.decode(io.read("*a"))==nil)' <"$f" 2>/dev/null; then
+ echo "Invalid JSON decoded without error: $f";
+ FAIL=1
+ fi
+done
+
+if [ "$FAIL" == "1" ]; then
+ echo "JSON tests failed"
+ exit 1;
+fi
+
+exit 0;
diff --git a/tests/test_util_multitable.lua b/tests/test_util_multitable.lua
index ed10b128..45727bc3 100644
--- a/tests/test_util_multitable.lua
+++ b/tests/test_util_multitable.lua
@@ -1,14 +1,14 @@
-- Prosody IM
-- Copyright (C) 2008-2010 Matthew Wild
-- Copyright (C) 2008-2010 Waqas Hussain
---
+--
-- This project is MIT/X11 licensed. Please see the
-- COPYING file in the source package for more information.
--
function new(new, multitable)
- mt = new();
+ local mt = new();
assert_table(mt, "Multitable is a table");
assert_function(mt.add, "Multitable has method add");
assert_function(mt.get, "Multitable has method get");
@@ -27,7 +27,7 @@ function get(get, multitable)
return true, "has-all";
end
for n=1,select('#', ...) do should_have[select(n, ...)] = true; end
- for n, item in ipairs(list) do
+ for _, item in ipairs(list) do
if not should_have[item] then return false, "too-many"; end
should_have[item] = nil;
end
@@ -40,8 +40,8 @@ function get(get, multitable)
return assert_equal(select(2, has_items(list, ...)), "has-all", message or "List has all expected items, and no more", 2);
end
- mt = multitable.new();
-
+ local mt = multitable.new();
+
local trigger1, trigger2, trigger3 = {}, {}, {};
local item1, item2, item3 = {}, {}, {};
@@ -51,12 +51,12 @@ function get(get, multitable)
mt:add(1, 2, 3, item1);
assert_has_all("Has item1 for 1, 2, 3", mt:get(1, 2, 3), item1);
-
+
-- Doesn't support nil
--[[ mt:add(nil, item1);
mt:add(nil, item2);
mt:add(nil, item3);
-
+
assert_has_all("Has all items with (nil)", mt:get(nil), item1, item2, item3);
]]
end
diff --git a/tests/test_util_queue.lua b/tests/test_util_queue.lua
new file mode 100644
index 00000000..e215ba33
--- /dev/null
+++ b/tests/test_util_queue.lua
@@ -0,0 +1,74 @@
+
+function new(new)
+ do
+ local q = new(10);
+
+ assert_equal(q.size, 10);
+ assert_equal(q:count(), 0);
+
+ assert_is(q:push("one"));
+ assert_is(q:push("two"));
+ assert_is(q:push("three"));
+
+ for i = 4, 10 do
+ assert_is(q:push("hello"));
+ assert_equal(q:count(), i, "count is not "..i.."("..q:count()..")");
+ end
+ assert_equal(q:push("hello"), nil, "queue overfull!");
+ assert_equal(q:push("hello"), nil, "queue overfull!");
+ assert_equal(q:pop(), "one", "queue item incorrect");
+ assert_equal(q:pop(), "two", "queue item incorrect");
+ assert_is(q:push("hello"));
+ assert_is(q:push("hello"));
+ assert_equal(q:pop(), "three", "queue item incorrect");
+ assert_is(q:push("hello"));
+ assert_equal(q:push("hello"), nil, "queue overfull!");
+ assert_equal(q:push("hello"), nil, "queue overfull!");
+
+ assert_equal(q:count(), 10, "queue count incorrect");
+
+ for _ = 1, 10 do
+ assert_equal(q:pop(), "hello", "queue item incorrect");
+ end
+
+ assert_equal(q:count(), 0, "queue count incorrect");
+
+ assert_is(q:push(1));
+ for i = 1, 1001 do
+ assert_equal(q:pop(), i);
+ assert_equal(q:count(), 0);
+ assert_is(q:push(i+1));
+ assert_equal(q:count(), 1);
+ end
+ assert_equal(q:pop(), 1002);
+ assert_is(q:push(1));
+ for i = 1, 1000 do
+ assert_equal(q:pop(), i);
+ assert_is(q:push(i+1));
+ end
+ assert_equal(q:pop(), 1001);
+ assert_equal(q:count(), 0);
+ end
+
+ do
+ -- Test queues that purge old items when pushing to a full queue
+ local q = new(10, true);
+
+ for i = 1, 10 do
+ q:push(i);
+ end
+
+ assert_equal(q:count(), 10);
+
+ assert_is(q:push(11));
+ assert_equal(q:count(), 10);
+ assert_equal(q:pop(), 2); -- First item should have been purged
+
+ for i = 12, 32 do
+ assert_is(q:push(i));
+ end
+
+ assert_equal(q:count(), 10);
+ assert_equal(q:pop(), 23);
+ end
+end
diff --git a/tests/test_util_random.lua b/tests/test_util_random.lua
new file mode 100644
index 00000000..79572ef8
--- /dev/null
+++ b/tests/test_util_random.lua
@@ -0,0 +1,10 @@
+-- Makes no attempt at testing how random the bytes are,
+-- just that it returns the number of bytes requested
+
+function bytes(bytes)
+ assert_is(bytes(16));
+
+ for i = 1, 255 do
+ assert_equal(i, #bytes(i));
+ end
+end
diff --git a/tests/test_util_rfc3484.lua b/tests/test_util_rfc3484.lua
deleted file mode 100644
index 18ae310e..00000000
--- a/tests/test_util_rfc3484.lua
+++ /dev/null
@@ -1,51 +0,0 @@
--- Prosody IM
--- Copyright (C) 2011 Florian Zeitz
---
--- This project is MIT/X11 licensed. Please see the
--- COPYING file in the source package for more information.
---
-
-function source(source)
- local new_ip = require"util.ip".new_ip;
- assert_equal(source(new_ip("2001::1", "IPv6"), {new_ip("3ffe::1", "IPv6"), new_ip("fe80::1", "IPv6")}).addr, "3ffe::1", "prefer appropriate scope");
- assert_equal(source(new_ip("2001::1", "IPv6"), {new_ip("fe80::1", "IPv6"), new_ip("fec0::1", "IPv6")}).addr, "fec0::1", "prefer appropriate scope");
- assert_equal(source(new_ip("fec0::1", "IPv6"), {new_ip("fe80::1", "IPv6"), new_ip("2001::1", "IPv6")}).addr, "2001::1", "prefer appropriate scope");
- assert_equal(source(new_ip("ff05::1", "IPv6"), {new_ip("fe80::1", "IPv6"), new_ip("fec0::1", "IPv6"), new_ip("2001::1", "IPv6")}).addr, "fec0::1", "prefer appropriate scope");
- assert_equal(source(new_ip("2001::1", "IPv6"), {new_ip("2001::1", "IPv6"), new_ip("2002::1", "IPv6")}).addr, "2001::1", "prefer same address");
- assert_equal(source(new_ip("fec0::1", "IPv6"), {new_ip("fec0::2", "IPv6"), new_ip("2001::1", "IPv6")}).addr, "fec0::2", "prefer appropriate scope");
- assert_equal(source(new_ip("2001::1", "IPv6"), {new_ip("2001::2", "IPv6"), new_ip("3ffe::2", "IPv6")}).addr, "2001::2", "longest matching prefix");
- assert_equal(source(new_ip("2002:836b:2179::1", "IPv6"), {new_ip("2002:836b:2179::d5e3:7953:13eb:22e8", "IPv6"), new_ip("2001::2", "IPv6")}).addr, "2002:836b:2179::d5e3:7953:13eb:22e8", "prefer matching label");
-end
-
-function destination(dest)
- local order;
- local new_ip = require"util.ip".new_ip;
- order = dest({new_ip("2001::1", "IPv6"), new_ip("131.107.65.121", "IPv4")}, {new_ip("2001::2", "IPv6"), new_ip("fe80::1", "IPv6"), new_ip("169.254.13.78", "IPv4")})
- assert_equal(order[1].addr, "2001::1", "prefer matching scope");
- assert_equal(order[2].addr, "131.107.65.121", "prefer matching scope")
-
- order = dest({new_ip("2001::1", "IPv6"), new_ip("131.107.65.121", "IPv4")}, {new_ip("fe80::1", "IPv6"), new_ip("131.107.65.117", "IPv4")})
- assert_equal(order[1].addr, "131.107.65.121", "prefer matching scope")
- assert_equal(order[2].addr, "2001::1", "prefer matching scope")
-
- order = dest({new_ip("2001::1", "IPv6"), new_ip("10.1.2.3", "IPv4")}, {new_ip("2001::2", "IPv6"), new_ip("fe80::1", "IPv6"), new_ip("10.1.2.4", "IPv4")})
- assert_equal(order[1].addr, "2001::1", "prefer higher precedence");
- assert_equal(order[2].addr, "10.1.2.3", "prefer higher precedence");
-
- order = dest({new_ip("2001::1", "IPv6"), new_ip("fec0::1", "IPv6"), new_ip("fe80::1", "IPv6")}, {new_ip("2001::2", "IPv6"), new_ip("fec0::1", "IPv6"), new_ip("fe80::2", "IPv6")})
- assert_equal(order[1].addr, "fe80::1", "prefer smaller scope");
- assert_equal(order[2].addr, "fec0::1", "prefer smaller scope");
- assert_equal(order[3].addr, "2001::1", "prefer smaller scope");
-
- order = dest({new_ip("2001::1", "IPv6"), new_ip("3ffe::1", "IPv6")}, {new_ip("2001::2", "IPv6"), new_ip("3f44::2", "IPv6"), new_ip("fe80::2", "IPv6")})
- assert_equal(order[1].addr, "2001::1", "longest matching prefix");
- assert_equal(order[2].addr, "3ffe::1", "longest matching prefix");
-
- order = dest({new_ip("2002:836b:4179::1", "IPv6"), new_ip("2001::1", "IPv6")}, {new_ip("2002:836b:4179::2", "IPv6"), new_ip("fe80::2", "IPv6")})
- assert_equal(order[1].addr, "2002:836b:4179::1", "prefer matching label");
- assert_equal(order[2].addr, "2001::1", "prefer matching label");
-
- order = dest({new_ip("2002:836b:4179::1", "IPv6"), new_ip("2001::1", "IPv6")}, {new_ip("2002:836b:4179::2", "IPv6"), new_ip("2001::2", "IPv6"), new_ip("fe80::2", "IPv6")})
- assert_equal(order[1].addr, "2001::1", "prefer higher precedence");
- assert_equal(order[2].addr, "2002:836b:4179::1", "prefer higher precedence");
-end
diff --git a/tests/test_util_rfc6724.lua b/tests/test_util_rfc6724.lua
new file mode 100644
index 00000000..bb73e921
--- /dev/null
+++ b/tests/test_util_rfc6724.lua
@@ -0,0 +1,97 @@
+-- Prosody IM
+-- Copyright (C) 2011-2013 Florian Zeitz
+--
+-- This project is MIT/X11 licensed. Please see the
+-- COPYING file in the source package for more information.
+--
+
+function source(source)
+ local new_ip = require"util.ip".new_ip;
+ assert_equal(source(new_ip("2001:db8:1::1", "IPv6"),
+ {new_ip("2001:db8:3::1", "IPv6"), new_ip("fe80::1", "IPv6")}).addr,
+ "2001:db8:3::1",
+ "prefer appropriate scope");
+ assert_equal(source(new_ip("ff05::1", "IPv6"),
+ {new_ip("2001:db8:3::1", "IPv6"), new_ip("fe80::1", "IPv6")}).addr,
+ "2001:db8:3::1",
+ "prefer appropriate scope");
+ assert_equal(source(new_ip("2001:db8:1::1", "IPv6"),
+ {new_ip("2001:db8:1::1", "IPv6"), new_ip("2001:db8:2::1", "IPv6")}).addr,
+ "2001:db8:1::1",
+ "prefer same address"); -- "2001:db8:1::1" should be marked "deprecated" here, we don't handle that right now
+ assert_equal(source(new_ip("fe80::1", "IPv6"),
+ {new_ip("fe80::2", "IPv6"), new_ip("2001:db8:1::1", "IPv6")}).addr,
+ "fe80::2",
+ "prefer appropriate scope"); -- "fe80::2" should be marked "deprecated" here, we don't handle that right now
+ assert_equal(source(new_ip("2001:db8:1::1", "IPv6"),
+ {new_ip("2001:db8:1::2", "IPv6"), new_ip("2001:db8:3::2", "IPv6")}).addr,
+ "2001:db8:1::2",
+ "longest matching prefix");
+--[[ "2001:db8:1::2" should be a care-of address and "2001:db8:3::2" a home address, we can't handle this and would fail
+ assert_equal(source(new_ip("2001:db8:1::1", "IPv6"),
+ {new_ip("2001:db8:1::2", "IPv6"), new_ip("2001:db8:3::2", "IPv6")}).addr,
+ "2001:db8:3::2",
+ "prefer home address");
+]]
+ assert_equal(source(new_ip("2002:c633:6401::1", "IPv6"),
+ {new_ip("2002:c633:6401::d5e3:7953:13eb:22e8", "IPv6"), new_ip("2001:db8:1::2", "IPv6")}).addr,
+ "2002:c633:6401::d5e3:7953:13eb:22e8",
+ "prefer matching label"); -- "2002:c633:6401::d5e3:7953:13eb:22e8" should be marked "temporary" here, we don't handle that right now
+ assert_equal(source(new_ip("2001:db8:1::d5e3:0:0:1", "IPv6"),
+ {new_ip("2001:db8:1::2", "IPv6"), new_ip("2001:db8:1::d5e3:7953:13eb:22e8", "IPv6")}).addr,
+ "2001:db8:1::d5e3:7953:13eb:22e8",
+ "prefer temporary address") -- "2001:db8:1::2" should be marked "public" and "2001:db8:1::d5e3:7953:13eb:22e8" should be marked "temporary" here, we don't handle that right now
+end
+
+function destination(dest)
+ local order;
+ local new_ip = require"util.ip".new_ip;
+ order = dest({new_ip("2001:db8:1::1", "IPv6"), new_ip("198.51.100.121", "IPv4")},
+ {new_ip("2001:db8:1::2", "IPv6"), new_ip("fe80::1", "IPv6"), new_ip("169.254.13.78", "IPv4")})
+ assert_equal(order[1].addr, "2001:db8:1::1", "prefer matching scope");
+ assert_equal(order[2].addr, "198.51.100.121", "prefer matching scope");
+
+ order = dest({new_ip("2001:db8:1::1", "IPv6"), new_ip("198.51.100.121", "IPv4")},
+ {new_ip("fe80::1", "IPv6"), new_ip("198.51.100.117", "IPv4")})
+ assert_equal(order[1].addr, "198.51.100.121", "prefer matching scope");
+ assert_equal(order[2].addr, "2001:db8:1::1", "prefer matching scope");
+
+ order = dest({new_ip("2001:db8:1::1", "IPv6"), new_ip("10.1.2.3", "IPv4")},
+ {new_ip("2001:db8:1::2", "IPv6"), new_ip("fe80::1", "IPv6"), new_ip("10.1.2.4", "IPv4")})
+ assert_equal(order[1].addr, "2001:db8:1::1", "prefer higher precedence");
+ assert_equal(order[2].addr, "10.1.2.3", "prefer higher precedence");
+
+ order = dest({new_ip("2001:db8:1::1", "IPv6"), new_ip("fe80::1", "IPv6")},
+ {new_ip("2001:db8:1::2", "IPv6"), new_ip("fe80::2", "IPv6")})
+ assert_equal(order[1].addr, "fe80::1", "prefer smaller scope");
+ assert_equal(order[2].addr, "2001:db8:1::1", "prefer smaller scope");
+
+--[[ "2001:db8:1::2" and "fe80::2" should be marked "care-of address", while "2001:db8:3::1" should be marked "home address", we can't currently handle this and would fail the test
+ order = dest({new_ip("2001:db8:1::1", "IPv6"), new_ip("fe80::1", "IPv6")},
+ {new_ip("2001:db8:1::2", "IPv6"), new_ip("2001:db8:3::1", "IPv6"), new_ip("fe80::2", "IPv6")})
+ assert_equal(order[1].addr, "2001:db8:1::1", "prefer home address");
+ assert_equal(order[2].addr, "fe80::1", "prefer home address");
+]]
+
+--[[ "fe80::2" should be marked "deprecated", we can't currently handle this and would fail the test
+ order = dest({new_ip("2001:db8:1::1", "IPv6"), new_ip("fe80::1", "IPv6")},
+ {new_ip("2001:db8:1::2", "IPv6"), new_ip("fe80::2", "IPv6")})
+ assert_equal(order[1].addr, "2001:db8:1::1", "avoid deprecated addresses");
+ assert_equal(order[2].addr, "fe80::1", "avoid deprecated addresses");
+]]
+
+ order = dest({new_ip("2001:db8:1::1", "IPv6"), new_ip("2001:db8:3ffe::1", "IPv6")},
+ {new_ip("2001:db8:1::2", "IPv6"), new_ip("2001:db8:3f44::2", "IPv6"), new_ip("fe80::2", "IPv6")})
+ assert_equal(order[1].addr, "2001:db8:1::1", "longest matching prefix");
+ assert_equal(order[2].addr, "2001:db8:3ffe::1", "longest matching prefix");
+
+ order = dest({new_ip("2002:c633:6401::1", "IPv6"), new_ip("2001:db8:1::1", "IPv6")},
+ {new_ip("2002:c633:6401::2", "IPv6"), new_ip("fe80::2", "IPv6")})
+ assert_equal(order[1].addr, "2002:c633:6401::1", "prefer matching label");
+ assert_equal(order[2].addr, "2001:db8:1::1", "prefer matching label");
+
+ order = dest({new_ip("2002:c633:6401::1", "IPv6"), new_ip("2001:db8:1::1", "IPv6")},
+ {new_ip("2002:c633:6401::2", "IPv6"), new_ip("2001:db8:1::2", "IPv6"), new_ip("fe80::2", "IPv6")})
+ assert_equal(order[1].addr, "2001:db8:1::1", "prefer higher precedence");
+ assert_equal(order[2].addr, "2002:c633:6401::1", "prefer higher precedence");
+end
diff --git a/tests/test_util_stanza.lua b/tests/test_util_stanza.lua
index fce26f3a..4be07a4b 100644
--- a/tests/test_util_stanza.lua
+++ b/tests/test_util_stanza.lua
@@ -1,7 +1,7 @@
-- Prosody IM
-- Copyright (C) 2008-2010 Matthew Wild
-- Copyright (C) 2008-2010 Waqas Hussain
---
+--
-- This project is MIT/X11 licensed. Please see the
-- COPYING file in the source package for more information.
--
@@ -18,10 +18,135 @@ end
function deserialize(deserialize, st)
local stanza = st.stanza("message", { a = "a" });
-
+
local stanza2 = deserialize(st.preserialize(stanza));
assert_is(stanza2 and stanza.name, "deserialize returns a stanza");
assert_table(stanza2.attr, "Deserialized stanza has attributes");
assert_equal(stanza2.attr.a, "a", "Deserialized stanza retains attributes");
assert_table(getmetatable(stanza2), "Deserialized stanza has metatable");
end
+
+function stanza(stanza)
+ local s = stanza("foo", { xmlns = "myxmlns", a = "attr-a" });
+ assert_equal(s.name, "foo");
+ assert_equal(s.attr.xmlns, "myxmlns");
+ assert_equal(s.attr.a, "attr-a");
+
+ local s1 = stanza("s1");
+ assert_equal(s1.name, "s1");
+ assert_equal(s1.attr.xmlns, nil);
+ assert_equal(#s1, 0);
+ assert_equal(#s1.tags, 0);
+
+ s1:tag("child1");
+ assert_equal(#s1.tags, 1);
+ assert_equal(s1.tags[1].name, "child1");
+
+ s1:tag("grandchild1"):up();
+ assert_equal(#s1.tags, 1);
+ assert_equal(s1.tags[1].name, "child1");
+ assert_equal(#s1.tags[1], 1);
+ assert_equal(s1.tags[1][1].name, "grandchild1");
+
+ s1:up():tag("child2");
+ assert_equal(#s1.tags, 2, tostring(s1));
+ assert_equal(s1.tags[1].name, "child1");
+ assert_equal(s1.tags[2].name, "child2");
+ assert_equal(#s1.tags[1], 1);
+ assert_equal(s1.tags[1][1].name, "grandchild1");
+
+ s1:up():text("Hello world");
+ assert_equal(#s1.tags, 2);
+ assert_equal(#s1, 3);
+ assert_equal(s1.tags[1].name, "child1");
+ assert_equal(s1.tags[2].name, "child2");
+ assert_equal(#s1.tags[1], 1);
+ assert_equal(s1.tags[1][1].name, "grandchild1");
+end
+
+function message(message)
+ local m = message();
+ assert_equal(m.name, "message");
+end
+
+function iq(iq)
+ local i = iq();
+ assert_equal(i.name, "iq");
+end
+
+function presence(presence)
+ local p = presence();
+ assert_equal(p.name, "presence");
+end
+
+function reply(reply, _M)
+ do
+ -- Test stanza
+ local s = _M.stanza("s", { to = "touser", from = "fromuser", id = "123" })
+ :tag("child1");
+ -- Make reply stanza
+ local r = reply(s);
+ assert_equal(r.name, s.name);
+ assert_equal(r.id, s.id);
+ assert_equal(r.attr.to, s.attr.from);
+ assert_equal(r.attr.from, s.attr.to);
+ assert_equal(#r.tags, 0, "A reply should not include children of the original stanza");
+ end
+
+ do
+ -- Test stanza
+ local s = _M.stanza("iq", { to = "touser", from = "fromuser", id = "123", type = "get" })
+ :tag("child1");
+ -- Make reply stanza
+ local r = reply(s);
+ assert_equal(r.name, s.name);
+ assert_equal(r.id, s.id);
+ assert_equal(r.attr.to, s.attr.from);
+ assert_equal(r.attr.from, s.attr.to);
+ assert_equal(r.attr.type, "result");
+ assert_equal(#r.tags, 0, "A reply should not include children of the original stanza");
+ end
+
+ do
+ -- Test stanza
+ local s = _M.stanza("iq", { to = "touser", from = "fromuser", id = "123", type = "set" })
+ :tag("child1");
+ -- Make reply stanza
+ local r = reply(s);
+ assert_equal(r.name, s.name);
+ assert_equal(r.id, s.id);
+ assert_equal(r.attr.to, s.attr.from);
+ assert_equal(r.attr.from, s.attr.to);
+ assert_equal(r.attr.type, "result");
+ assert_equal(#r.tags, 0, "A reply should not include children of the original stanza");
+ end
+end
+
+function error_reply(error_reply, _M)
+ do
+ -- Test stanza
+ local s = _M.stanza("s", { to = "touser", from = "fromuser", id = "123" })
+ :tag("child1");
+ -- Make reply stanza
+ local r = error_reply(s);
+ assert_equal(r.name, s.name);
+ assert_equal(r.id, s.id);
+ assert_equal(r.attr.to, s.attr.from);
+ assert_equal(r.attr.from, s.attr.to);
+ assert_equal(#r.tags, 1);
+ end
+
+ do
+ -- Test stanza
+ local s = _M.stanza("iq", { to = "touser", from = "fromuser", id = "123", type = "get" })
+ :tag("child1");
+ -- Make reply stanza
+ local r = error_reply(s);
+ assert_equal(r.name, s.name);
+ assert_equal(r.id, s.id);
+ assert_equal(r.attr.to, s.attr.from);
+ assert_equal(r.attr.from, s.attr.to);
+ assert_equal(r.attr.type, "error");
+ assert_equal(#r.tags, 1);
+ end
+end
diff --git a/tests/test_util_throttle.lua b/tests/test_util_throttle.lua
new file mode 100644
index 00000000..6d47238a
--- /dev/null
+++ b/tests/test_util_throttle.lua
@@ -0,0 +1,26 @@
+
+local now = 0; -- wibbly-wobbly... timey-wimey... stuff
+local function predictable_gettime()
+ return now;
+end
+local function later(n)
+ now = now + n; -- time passes at a different rate
+end
+
+package.loaded["util.time"] = {
+ now = predictable_gettime;
+}
+
+function create(create)
+ local a = create(3, 10);
+
+ assert_equal(a:poll(1), true); -- 3 -> 2
+ assert_equal(a:poll(1), true); -- 2 -> 1
+ assert_equal(a:poll(1), true); -- 1 -> 0
+ assert_equal(a:poll(1), false); -- MEEP, out of credits!
+ later(1); -- ... what about
+ assert_equal(a:poll(1), false); -- now? - Still no!
+ later(9); -- Later that day
+ assert_equal(a:poll(1), true); -- Should be back at 3 credits ... 2
+end
+
diff --git a/tests/test_util_uuid.lua b/tests/test_util_uuid.lua
new file mode 100644
index 00000000..07d75025
--- /dev/null
+++ b/tests/test_util_uuid.lua
@@ -0,0 +1,24 @@
+-- This tests the format, not the randomness
+
+-- https://tools.ietf.org/html/rfc4122#section-4.4
+
+local pattern = "^" .. table.concat({
+ string.rep("%x", 8),
+ string.rep("%x", 4),
+ "4" .. -- version
+ string.rep("%x", 3),
+ "[89ab]" .. -- reserved bits of 1 and 0
+ string.rep("%x", 3),
+ string.rep("%x", 12),
+}, "%-") .. "$";
+
+function generate(generate)
+ for _ = 1, 100 do
+ assert_is(generate():match(pattern));
+ end
+end
+
+function seed(seed)
+ assert_equal(seed("random string here"), nil, "seed doesn't return anything");
+end
+
diff --git a/tests/test_util_xml.lua b/tests/test_util_xml.lua
new file mode 100644
index 00000000..ba44da19
--- /dev/null
+++ b/tests/test_util_xml.lua
@@ -0,0 +1,12 @@
+function parse(parse)
+ local x =
+[[<x xmlns:a="b">
+ <y xmlns:a="c"> <!-- this overwrites 'a' -->
+ <a:z/>
+ </y>
+ <a:z/> <!-- prefix 'a' is nil here, but should be 'b' -->
+</x>
+]]
+ local stanza = parse(x);
+ assert_equal(stanza.tags[2].attr.xmlns, "b");
+end
diff --git a/tests/test_util_xmppstream.lua b/tests/test_util_xmppstream.lua
new file mode 100644
index 00000000..791cf999
--- /dev/null
+++ b/tests/test_util_xmppstream.lua
@@ -0,0 +1,83 @@
+function new(new_stream, _M)
+ local function test(xml, expect_success, ex)
+ local stanzas = {};
+ local session = { notopen = true };
+ local callbacks = {
+ stream_ns = "streamns";
+ stream_tag = "stream";
+ default_ns = "stanzans";
+ streamopened = function (_session)
+ assert_equal(session, _session);
+ assert_equal(session.notopen, true);
+ _session.notopen = nil;
+ return true;
+ end;
+ handlestanza = function (_session, stanza)
+ assert_equal(session, _session);
+ assert_equal(_session.notopen, nil);
+ table.insert(stanzas, stanza);
+ end;
+ streamclosed = function (_session)
+ assert_equal(session, _session);
+ assert_equal(_session.notopen, nil);
+ _session.notopen = nil;
+ end;
+ }
+ if type(ex) == "table" then
+ for k, v in pairs(ex) do
+ if k ~= "_size_limit" then
+ callbacks[k] = v;
+ end
+ end
+ end
+ local stream = new_stream(session, callbacks, size_limit);
+ local ok, err = pcall(function ()
+ assert(stream:feed(xml));
+ end);
+
+ if ok and type(expect_success) == "function" then
+ expect_success(stanzas);
+ end
+ assert_equal(not not ok, not not expect_success, "Expected "..(expect_success and ("success ("..tostring(err)..")") or "failure"));
+ end
+
+ local function test_stanza(stanza, expect_success, ex)
+ return test([[<stream:stream xmlns:stream="streamns" xmlns="stanzans">]]..stanza, expect_success, ex);
+ end
+
+ test([[<stream:stream xmlns:stream="streamns"/>]], true);
+ test([[<stream xmlns="streamns"/>]], true);
+
+ test([[<stream1 xmlns="streamns"/>]], false);
+ test([[<stream xmlns="streamns1"/>]], false);
+ test("<>", false);
+
+ test_stanza("<message/>", function (stanzas)
+ assert_equal(#stanzas, 1);
+ assert_equal(stanzas[1].name, "message");
+ end);
+ test_stanza("< message>>>>/>\n", false);
+
+ test_stanza([[<x xmlns:a="b">
+ <y xmlns:a="c">
+ <a:z/>
+ </y>
+ <a:z/>
+ </x>]], function (stanzas)
+ assert_equal(#stanzas, 1);
+ local s = stanzas[1];
+ assert_equal(s.name, "x");
+ assert_equal(#s.tags, 2);
+
+ assert_equal(s.tags[1].name, "y");
+ assert_equal(s.tags[1].attr.xmlns, nil);
+
+ assert_equal(s.tags[1].tags[1].name, "z");
+ assert_equal(s.tags[1].tags[1].attr.xmlns, "c");
+
+ assert_equal(s.tags[2].name, "z");
+ assert_equal(s.tags[2].attr.xmlns, "b");
+
+ assert_equal(s.namespaces, nil);
+ end);
+end
diff --git a/tests/util/logger.lua b/tests/util/logger.lua
index 35facd4e..44860d5d 100644
--- a/tests/util/logger.lua
+++ b/tests/util/logger.lua
@@ -1,7 +1,7 @@
-- Prosody IM
-- Copyright (C) 2008-2010 Matthew Wild
-- Copyright (C) 2008-2010 Waqas Hussain
---
+--
-- This project is MIT/X11 licensed. Please see the
-- COPYING file in the source package for more information.
--
@@ -14,7 +14,8 @@ local tostring = tostring;
local getstyle, getstring = require "util.termcolours".getstyle, require "util.termcolours".getstring;
local do_pretty_printing = not os.getenv("WINDIR");
-module "logger"
+local _ENV = nil
+local _M = {}
local logstyles = {};
@@ -25,7 +26,7 @@ if do_pretty_printing then
logstyles["error"] = getstyle("bold", "red");
end
-function init(name)
+function _M.init(name)
--name = nil; -- While this line is not commented, will automatically fill in file/line number info
return function (level, message, ...)
if level == "debug" or level == "info" then return; end