summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authordeva <deva>2008-06-09 06:49:58 +0000
committerdeva <deva>2008-06-09 06:49:58 +0000
commite80ccdfac750fdd318eecb35b5f48a3d251ec7ec (patch)
treec296fb042d17f75aad06ff95e5f48dcb8143dabd
parentc3a7893d9f2c67614257bc0dbfa802b9cc9ff056 (diff)
Made output accumulation in a buffer and write in the end, thus enabling the corretc outputting of the error box if neccessary.
-rw-r--r--server/src/database.h1
-rw-r--r--server/src/luaquerymapper.cc79
-rw-r--r--server/src/luaquerymapper.h2
-rw-r--r--server/src/server.cc32
-rw-r--r--server/src/widgetgenerator.cc35
-rw-r--r--server/src/widgetgenerator.h7
-rw-r--r--server/xml/macros/example.xml43
7 files changed, 111 insertions, 88 deletions
diff --git a/server/src/database.h b/server/src/database.h
index 8200129..31d69fc 100644
--- a/server/src/database.h
+++ b/server/src/database.h
@@ -38,6 +38,7 @@
class Value {
public:
+ Value() : value(""), timestamp(0) {}
std::string value;
time_t timestamp;
};
diff --git a/server/src/luaquerymapper.cc b/server/src/luaquerymapper.cc
index df25778..5b66a35 100644
--- a/server/src/luaquerymapper.cc
+++ b/server/src/luaquerymapper.cc
@@ -28,6 +28,8 @@
#include <sstream>
+#include "exception.h"
+
static std::string loadresultstring(QueryResult &res, std::string group = "")
{
std::string s;
@@ -55,29 +57,24 @@ LUAQueryMapper::LUAQueryMapper(QueryResult &res)
{
L = luaL_newstate();
if(L == NULL) {
- // throw LUADataParserException("Could not create LUA state.");
+ error("Could not create LUA state.");
+ return;
}
luaL_openlibs(L);
std::string preload = loadresultstring(res);
- int s = luaL_loadbuffer(L, preload.c_str(), preload.size(), "preload");
- switch(s) {
- case 0: //no errors;
- break;
- case LUA_ERRSYNTAX: //syntax error during pre-compilation;
- case LUA_ERRMEM: //memory allocation error.
- case LUA_ERRFILE: //cannot open/read the file.
- //throw LUADataParserException(lua_tostring(L, lua_gettop(L)));
- break;
- default:
- //throw LUADataParserException("Unknown return value of luaL_loadfile.");
- break;
+ if(luaL_loadbuffer(L, preload.c_str(), preload.size(), "preload")) {
+ error(lua_tostring(L, lua_gettop(L)));
+ return;
}
// Run program (init)
- lua_pcall(L, 0, LUA_MULTRET, 0);
+ if(lua_pcall(L, 0, LUA_MULTRET, 0)) {
+ error(lua_tostring(L, lua_gettop(L)));
+ return;
+ }
clean_top = lua_gettop(L);
}
@@ -91,47 +88,61 @@ Value LUAQueryMapper::map(const std::string &mapper)
{
Value v;
+ if(L == NULL) {
+ error("LUA state not initialized!");
+ return v;
+ }
+
if(mapper == "") {
- printf("Empty LUA mapper detected!\n");
- v.timestamp = 0;
- v.value = "";
+ error("Empty LUA mapper detected in " + mapper);
+ return v;
}
- int s = luaL_loadbuffer(L, mapper.c_str(), mapper.size(), "mapper");
- switch(s) {
- case 0: //no errors;
- break;
- case LUA_ERRSYNTAX: //syntax error during pre-compilation;
- case LUA_ERRMEM: //memory allocation error.
- case LUA_ERRFILE: //cannot open/read the file.
- //throw LUADataParserException(lua_tostring(L, lua_gettop(L)));
- break;
- default:
- //throw LUADataParserException("Unknown return value of luaL_loadfile.");
- break;
+ // Load the mapper
+ if(luaL_loadbuffer(L, mapper.c_str(), mapper.size(), "mapper")) {
+ error(lua_tostring(L, lua_gettop(L)) + std::string(" in ") + mapper);
+ return v;
}
// Run the loaded code
- lua_pcall(L, 0, LUA_MULTRET, 0);
+ if(lua_pcall(L, 0, LUA_MULTRET, 0)) {
+ error(lua_tostring(L, lua_gettop(L)) + std::string(" in ") + mapper);
+ return v;
+ }
// Check if app messed up the stack.
if(lua_gettop(L) != clean_top + 2) {
- printf("LUA mapper messed up the stack (wrong number of return values)!\n");
+ error("Wrong number of return values in " + mapper);
lua_pop(L, lua_gettop(L) - clean_top);
- Value v;
- v.timestamp = 0;
- v.value = "";
return v;
}
+ // Check if the types are right
+ if(lua_isnumber(L, lua_gettop(L)) == false) {
+ error("Timestamp is not an integer in " + mapper);
+ lua_pop(L, 2);
+ return v;
+ }
v.timestamp = lua_tointeger(L, lua_gettop(L));
lua_pop(L, 1);
+
+ // Check if the types are right
+ if(lua_isstring(L, lua_gettop(L)) == false) {
+ error("Value is not a string in " + mapper);
+ lua_pop(L, 1);
+ return v;
+ }
v.value = lua_tostring(L, lua_gettop(L));
lua_pop(L, 1);
return v;
}
+void LUAQueryMapper::error(std::string message)
+{
+ throw Exception("ERROR in LUAQueryMapper: " + message);
+}
+
#ifdef TEST_LUAQUERYMAPPER
#include "queryhandler.h"
diff --git a/server/src/luaquerymapper.h b/server/src/luaquerymapper.h
index 83866a0..685abe7 100644
--- a/server/src/luaquerymapper.h
+++ b/server/src/luaquerymapper.h
@@ -50,6 +50,8 @@ public:
*/
Value map(const std::string &mapper);
+ void error(std::string message);
+
private:
lua_State *L;
int clean_top;
diff --git a/server/src/server.cc b/server/src/server.cc
index 9708f9f..2ea782d 100644
--- a/server/src/server.cc
+++ b/server/src/server.cc
@@ -115,6 +115,8 @@ static void connection(TCPSocket &socket)
while(i != transaction.requests.end()) {
Request &request = *i;
+ std::string answer;
+
MacroParser mp(request.macro);
mp.parse();
Macro *m = mp.getMacro();
@@ -156,51 +158,47 @@ static void connection(TCPSocket &socket)
// Map the results
LUAQueryMapper lqm(qp.result);
- socket.write(" <course name=\"");
- socket.write(templ->course.attributes["name"]);
- socket.write("\">\n");
+ answer += " <course name=\"";
+ answer += templ->course.attributes["name"];
+ answer += "\">\n";
// Generate the macro and return it to the client
std::vector< Macro >::iterator mi2 = templ->course.macroes.begin();
while(mi2 != templ->course.macroes.end()) {
Macro &macro = (*mi2);
- socket.write(" <macro name=\"");
- socket.write(macro.attributes["name"]);
- socket.write("\">\n");
+ answer += " <macro name=\"" + macro.attributes["name"] + "\">\n";
if(macro.attributes["name"] == request.macro) {
// Handle lua programs
if(m->luaprograms.size()) {
- socket.write(" <luaprograms>\n");
+ answer += " <luaprograms>\n";
std::vector< LUAProgram >::iterator lpi = m->luaprograms.begin();
while(lpi != m->luaprograms.end()) {
- socket.write(" <luaprogram name=\"");
- socket.write(lpi->attributes["name"]);
- socket.write("\">\n");
+ answer += " <luaprogram name=\"" + lpi->attributes["name"] + "\">\n";
- socket.write(lpi->attributes["lua"]);
+ answer += lpi->attributes["lua"];
- socket.write("\n </luaprogram>\n");
+ answer += "\n </luaprogram>\n";
lpi++;
}
- socket.write(" </luaprograms>\n");
+ answer += " </luaprograms>\n";
}
- widgetgenerator(socket, *m, lqm, db);
+ answer += widgetgenerator(*m, lqm, db);
}
- socket.write(" </macro>\n");
+ answer += " </macro>\n";
mi2++;
}
- socket.write(" </course>\n");
-
+ answer += " </course>\n";
+ socket.write(answer);
i++;
}
} catch(std::exception &e) {
diff --git a/server/src/widgetgenerator.cc b/server/src/widgetgenerator.cc
index 6234513..43b202f 100644
--- a/server/src/widgetgenerator.cc
+++ b/server/src/widgetgenerator.cc
@@ -26,17 +26,18 @@
*/
#include "widgetgenerator.h"
-static void send_macro_widget(Macro &macro,
- Widget &widget,
- TCPSocket &socket,
- std::string tabs,
- LUAQueryMapper &mapper,
- Values &values)
+static std::string send_macro_widget(Macro &macro,
+ Widget &widget,
+ std::string tabs,
+ LUAQueryMapper &mapper,
+ Values &values)
{
+ std::string result;
+
std::string prefilled;
time_t timestamp = 0;
- socket.write(tabs + "<" + widget.attributes["type"]);
+ result = tabs + "<" + widget.attributes["type"];
std::map< std::string, std::string >::iterator p = widget.attributes.begin();
// Check if the field has a map, and fill in the value if it has...
@@ -72,26 +73,28 @@ static void send_macro_widget(Macro &macro,
while(p != widget.attributes.end()) {
if(p->first != "type" && p->first != "map") {
- socket.write(" " + p->first + "=\"" + p->second + "\"");
+ result += " " + p->first + "=\"" + p->second + "\"";
}
p++;
}
- if(prefilled != "") socket.write(" prefilled=\"" + prefilled + "\"");
+ if(prefilled != "") result += " prefilled=\"" + prefilled + "\"";
if(widget.widgets.size() == 0) { // If node is empty, use short tag form
- socket.write("/>\n");
- return;
+ result += "/>\n";
+ return result;
}
- socket.write(">\n");
+ result += ">\n";
std::vector< Widget >::iterator w = widget.widgets.begin();
while(w != widget.widgets.end()) {
- send_macro_widget(macro, *w, socket, tabs + " ", mapper, values);
+ result += send_macro_widget(macro, *w, tabs + " ", mapper, values);
w++;
}
- socket.write(tabs + "</" + widget.attributes["type"] + ">\n");
+ result += tabs + "</" + widget.attributes["type"] + ">\n";
+
+ return result;
}
static void get_fields(Widget &widget, Fieldnames &fields)
@@ -107,12 +110,12 @@ static void get_fields(Widget &widget, Fieldnames &fields)
}
}
-void widgetgenerator(TCPSocket &socket, Macro &macro, LUAQueryMapper &mapper, Database &db)
+std::string widgetgenerator(Macro &macro, LUAQueryMapper &mapper, Database &db)
{
Fieldnames fields;
get_fields(macro.window, fields);
Values values = db.getValues("2003791613", fields);
- send_macro_widget(macro, macro.window, socket, " ", mapper, values);
+ return send_macro_widget(macro, macro.window, " ", mapper, values);
}
diff --git a/server/src/widgetgenerator.h b/server/src/widgetgenerator.h
index 2ed77df..66d3690 100644
--- a/server/src/widgetgenerator.h
+++ b/server/src/widgetgenerator.h
@@ -34,9 +34,8 @@
#include "luaquerymapper.h"
#include "database.h"
-void widgetgenerator(TCPSocket &socket,
- Macro &macro,
- LUAQueryMapper &mapper,
- Database &db);
+std::string widgetgenerator(Macro &macro,
+ LUAQueryMapper &mapper,
+ Database &db);
#endif/*__PRACRO_WIDGETGENERATOR_H__*/
diff --git a/server/xml/macros/example.xml b/server/xml/macros/example.xml
index ce6e2c0..635dea2 100644
--- a/server/xml/macros/example.xml
+++ b/server/xml/macros/example.xml
@@ -1,5 +1,5 @@
<?xml version='1.0' encoding='UTF-8'?>
-<macro name="example" version="1.0" resume="${linse1}${linse2}">
+<macro name="example" version="1.0" resume="Axis: ${axis}\nCylinder: ${cyl}\nSphere: ${sphere}\n">
<queries>
<query class="lensmeter" ttl="10000" automap="true"/>
</queries>
@@ -8,12 +8,6 @@
-- LUA program
return math.pi, 1234567890
</map>
- <map name="right.axis" uses="lensmeter, lensmeter.right.axis">
- -- LUA program
- right_axis = 0
- if( lensmeter.right.axis ) right_axis = lensmeter.right.axis.value
- return right_axis, lensmeter.right.sphere.timestamp
- </map>
<map name="cyl">
-- LUA program
return lensmeter.right.cyl.value, lensmeter.right.cyl.timestamp
@@ -21,10 +15,11 @@
</maps>
<luaprograms>
<luaprogram name="theanswer">
- fisk = getValue('sphere')
- if( tonumber(fisk) == tonumber(value) )
+ sphere = tonumber(getValue('sphere'))
+ axis = tonumber(getValue('axis'))
+ if( sphere == axis )
then
- setValue('cyl', value)
+ setValue('cyl', name)
return true
else
return false
@@ -32,24 +27,38 @@
</luaprogram>
</luaprograms>
<window name="mainwindow"
- caption="Fundus"
- width="500"
- height="560"
+ caption="Example Window"
+ width="300"
+ height="400"
layout="vbox">
<frame name="linse_frame" caption="Linser:" layout="vbox">
<frame name="linse_framea" layout="hbox">
- <label name="a" width="300" caption="Akse rotation:"/>
+ <label name="a" width="100" caption="Akse rotation:"/>
<lineedit name="axis" regexp="[24]*" map="axis" lua="theanswer" value="244"/>
</frame>
<frame name="linse_frameb" layout="hbox">
- <label name="b" width="300" caption="Sphere:"/>
- <lineedit name="sphere" regexp="[24]*" map="sphere" value="42"/>
+ <label name="b" width="100" caption="Sphere:"/>
+ <lineedit name="sphere" regexp="[24]*" lua="theanswer" value="42"/>
</frame>
<frame name="linse_framec" layout="hbox">
- <label name="c" width="300" caption="Cyl:"/>
+ <label name="c" width="100" caption="Cyl:"/>
<lineedit name="cyl" regexp="[24]*" map="cyl" value=""/>
</frame>
</frame>
+ <frame name="linse_frame" caption="FlereLinser:" layout="vbox">
+ <frame name="linse_framea" layout="hbox">
+ <label name="a" width="100" caption="Akse rotation2:"/>
+ <lineedit name="axis2" regexp="[24]*" map="axis" lua="theanswer" value="244"/>
+ </frame>
+ <frame name="linse_frameb" layout="hbox">
+ <label name="b" width="100" caption="Sphere2:"/>
+ <lineedit name="sphere2" regexp="[24]*" lua="theanswer" value="42"/>
+ </frame>
+ <frame name="linse_framec" layout="hbox">
+ <label name="c" width="100" caption="Cyl2:"/>
+ <lineedit name="cyl2" regexp="[24]*" map="cyl" value=""/>
+ </frame>
+ </frame>
<frame name="buttons" layout="hbox">
<button name="cancel" caption="Annuller" action="cancel"/>
<button name="commit" caption="Godkend" action="commit"/>