summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorEdwin Mons <edwin.mons@isode.com>2016-09-22 10:09:49 (GMT)
committerKevin Smith <kevin.smith@isode.com>2016-10-19 19:11:45 (GMT)
commit08a340dbfc9208d1c0e6d574fed244a98e104f01 (patch)
tree936263f06740ee377928c18abdc4ee0a156bcf44
parentbcd3660a3527327117b46e104d16204a64fe0b9f (diff)
downloadswift-08a340dbfc9208d1c0e6d574fed244a98e104f01.zip
swift-08a340dbfc9208d1c0e6d574fed244a98e104f01.tar.bz2
Always add a fields table member in FormConvertor
The fields member of the forms generated by FormConvertor is used for lookups in the __index metafunction. If a form is parsed with no fields (and possibly no items), there wouldn't be a member 'fields', causing another __index lookup, triggering infinite recursion. There will now always be a fields array, which may be empty. Sluift/Tests/FormTest.lua has been updated to test against an empty form. Test-Information: Updated FormTest.lua works without issues. Change-Id: Idee98f23bf42e1213ca3d03707f908ed5317dad6
-rw-r--r--Sluift/ElementConvertors/FormConvertor.cpp4
-rw-r--r--Sluift/Tests/FormTest.lua14
2 files changed, 14 insertions, 4 deletions
diff --git a/Sluift/ElementConvertors/FormConvertor.cpp b/Sluift/ElementConvertors/FormConvertor.cpp
index a0e3dfe..85f40a1 100644
--- a/Sluift/ElementConvertors/FormConvertor.cpp
+++ b/Sluift/ElementConvertors/FormConvertor.cpp
@@ -260,63 +260,61 @@ namespace {
lua_pop(L, 1);
lua_getfield(L, -1, "items");
if (lua_istable(L, -1)) {
for (lua_pushnil(L); lua_next(L, -2);) {
result->addItem(convertFieldListFromLua(L));
lua_pop(L, 1);
}
}
lua_pop(L, 1);
return result;
}
void convertFormToLua(lua_State* L, std::shared_ptr<Form> payload) {
std::string type;
switch (payload->getType()) {
case Form::FormType: type = "form"; break;
case Form::SubmitType: type = "submit"; break;
case Form::CancelType: type = "cancel"; break;
case Form::ResultType: type = "result"; break;
}
Lua::Table result = boost::assign::map_list_of("type", Lua::valueRef(type));
if (!payload->getTitle().empty()) {
result["title"] = Lua::valueRef(payload->getTitle());
}
if (!payload->getInstructions().empty()) {
result["instructions"] = Lua::valueRef(payload->getInstructions());
}
- if (!payload->getFields().empty()) {
- result["fields"] = valueRef(convertFieldListToLua(payload->getFields()));
- }
+ result["fields"] = valueRef(convertFieldListToLua(payload->getFields()));
if (!payload->getReportedFields().empty()) {
result["reported_fields"] = valueRef(convertFieldListToLua(payload->getReportedFields()));
}
if (!payload->getItems().empty()) {
Lua::Array luaItems;
foreach(const Form::FormItem& item, payload->getItems()) {
if (!item.empty()) {
luaItems.push_back(convertFieldListToLua(item));
}
}
result["items"] = valueRef(luaItems);
}
Lua::pushValue(L, result);
lua_newtable(L);
lua_pushcfunction(L, formIndex);
lua_setfield(L, -2, "__index");
lua_pushcfunction(L, formNewIndex);
lua_setfield(L, -2, "__newindex");
lua_setmetatable(L, -2);
}
int createSubmission(lua_State* L) {
std::shared_ptr<Form> form = convertFormFromLua(L);
// Remove all redundant elements
form->setInstructions("");
form->setTitle("");
diff --git a/Sluift/Tests/FormTest.lua b/Sluift/Tests/FormTest.lua
index 8065360..d584646 100644
--- a/Sluift/Tests/FormTest.lua
+++ b/Sluift/Tests/FormTest.lua
@@ -1,32 +1,32 @@
--[[
- Copyright (c) 2013 Isode Limited.
+ Copyright (c) 2013-2016 Isode Limited.
All rights reserved.
See the COPYING file for more information.
--]]
example_form = [[
<x xmlns='jabber:x:data' type='form'>
<title>Bot Configuration</title>
<instructions>Fill out this form to configure your new bot!</instructions>
<field type='hidden' var='FORM_TYPE'>
<value>jabber:bot</value>
</field>
<field type='fixed'><value>Section 1: Bot Info</value></field>
<field type='text-single' label='The name of your bot' var='botname'/>
<field type='text-multi' label='Helpful description of your bot' var='description'>
<value>This is</value>
<value>my bot</value>
</field>
<field type='boolean' label='Public bot?' var='public'>
<required/>
</field>
<field type='text-private' label='Password for special access' var='password'/>
<field type='fixed'><value>Section 2: Features</value></field>
<field type='list-multi' label='What features will the bot support?' var='features'>
<option label='Contests'><value>contests</value></option>
<option label='News'><value>news</value></option>
<option label='Polls'><value>polls</value></option>
<option label='Reminders'><value>reminders</value></option>
<option label='Search'><value>search</value></option>
<value>news</value>
<value>search</value>
@@ -63,30 +63,42 @@ assert(public_field['required'] == true)
features_field = form['fields'][8]
assert(features_field['name'] == 'features')
assert(type(features_field['value']) == 'table')
assert(#features_field['value'] == 2)
assert(features_field['value'][1] == 'news')
assert(features_field['value'][2] == 'search')
-- Test shortcut index
assert(form['features']['name'] == 'features')
assert(form['FORM_TYPE']['value'] == 'jabber:bot')
-- Test response form
submission = form:create_submission()
assert(#(submission.fields) == 8)
description_submit_value = submission['description']['value']
assert(type(description_submit_value) == 'table')
assert(description_submit_value[1] == 'This is')
assert(description_submit_value[2] == 'my bot')
submission['description'] = 'my description'
assert(submission['description']['value'] == 'my description')
submission['type'] = 'cancel'
-- Test text-multi field
text_multi_field = form['fields'][4]
assert(text_multi_field['name'] == 'description')
assert(type(text_multi_field['value']) == 'table')
--print(sluift.to_xml({type = 'form', data = form}))
+
+-- test parsing an empty form -- this had issues as reported in SWIFT-174
+empty_form = [[<x xmlns='jabber:x:data' type='form'/>]]
+form = sluift.from_xml(empty_form)
+-- and check if we can access all fields without problems
+assert(type(form._type))
+assert(type(form.title))
+assert(type(form.instructions))
+assert(type(form.type))
+assert(type(form.fields))
+assert(type(form.items))
+assert(type(form.reported_items))