Switch from json-glib to json-c in websocketsink, pluginloader, and mappropertytype
authorMichael Carpenter <malcom2073@gmail.com>
Fri, 15 Mar 2013 02:01:31 +0000 (22:01 -0400)
committerMichael Carpenter <malcom2073@gmail.com>
Fri, 15 Mar 2013 02:01:31 +0000 (22:01 -0400)
ambd/pluginloader.cpp
lib/mappropertytype.hpp
plugins/websocketsink/websocketsinkmanager.cpp

index c310456..c06d60b 100644 (file)
@@ -22,7 +22,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
 
 #include <iostream>
 #include <stdexcept>
-#include <json-glib/json-glib.h>
+//#include <json-glib/json-glib.h>
 
 
 using namespace std;
@@ -38,33 +38,33 @@ using namespace std;
 
 PluginLoader::PluginLoader(string configFile, AbstractRoutingEngine* re, int argc, char** argv): f_create(NULL), routingEngine(re), mMainLoop(nullptr)
 {
+  
        DebugOut()<<"Loading config file: "<<configFile<<endl;
-       
-       JsonParser* parser = json_parser_new();
-       GError* error = nullptr;
-       if(!json_parser_load_from_file(parser, configFile.c_str(), &error))
+       json_object *rootobject;
+       json_tokener *tokener = json_tokener_new();
+       enum json_tokener_error err;
+       do
+       {
+               rootobject = json_tokener_parse_ex(tokener, configFile.c_str(),configFile.length());
+       } while ((err = json_tokener_get_error(tokener)) == json_tokener_continue);
+       if (err != json_tokener_success)
        {
-               DebugOut()<<"Failed to load config: "<<error->message;
-               throw std::runtime_error("Failed to load config");
+               fprintf(stderr, "Error: %s\n", json_tokener_error_desc(err));
+               // Handle errors, as appropriate for your application.
+       }
+       if (tokener->char_offset < configFile.length()) // XXX shouldn't access internal fields
+       {
+               // Handle extra characters after parsed object as desired.
+               // e.g. issue an error, parse another object from that point, etc...
        }
        
-       JsonNode* node = json_parser_get_root(parser);
-       
-       if(node == nullptr)
-               throw std::runtime_error("Unable to get JSON root object");
-       
-       JsonReader* reader = json_reader_new(node);
-       
-       if(reader == nullptr)
-               throw std::runtime_error("Unable to create JSON reader");
-       
-       DebugOut()<<"Config members: "<<json_reader_count_members(reader)<<endl;
-
-       if(json_reader_read_member(reader,"mainloop"))
+       //DebugOut()<<"Config members: "<<json_reader_count_members(reader)<<endl;
+       json_object *mainloopobject = json_object_object_get(rootobject,"mainloop");
+       if (mainloopobject)
        {
                /// there is a mainloop entry.  Load the plugin:
 
-               string mainloopstr = json_reader_get_string_value(reader);
+               string mainloopstr = string(json_object_get_string(mainloopobject));
 
                mMainLoop = loadMainLoop(mainloopstr,argc, argv);
 
@@ -80,39 +80,33 @@ PluginLoader::PluginLoader(string configFile, AbstractRoutingEngine* re, int arg
                mMainLoop = new GlibMainLoop(argc,argv);
        }
        
-       json_reader_end_member(reader);
+       json_object *sourcesobject = json_object_object_get(rootobject,"sources");
 
-       if(!json_reader_read_member(reader,"sources"))
+       if(!sourcesobject)
        {
-
-               const GError * srcReadError = json_reader_get_error(reader);
-
-               DebugOut()<<"Error getting sources member: "<<srcReadError->message<<endl;
+               DebugOut()<<"Error getting sources member: "<<endl;
                throw std::runtime_error("Error getting sources member");
        }
        
-       g_assert(json_reader_is_array(reader));
+       //g_assert(json_reader_is_array(reader));
+       g_assert(json_object_get_type(sourcesobject)==json_type_array);
+       
        
+       array_list *sourceslist = json_object_get_array(sourcesobject);
        
-       for(int i=0; i < json_reader_count_elements(reader); i++)
+       for(int i=0; i < array_list_length(sourceslist); i++)
        {
-               json_reader_read_element(reader,i);
+               json_object *obj = (json_object*)array_list_get_idx(sourceslist,i); //This is an object
                
-               gchar** srcMembers = json_reader_list_members(reader);
-
                std::map<std::string, std::string> configurationMap;
-
-               for(int i=0; i< json_reader_count_members(reader); i++)
+               json_object_object_foreach(obj, key, val)
                {
-                       json_reader_read_member(reader,srcMembers[i]);
-                       configurationMap[srcMembers[i]] = json_reader_get_string_value(reader);
-                       DebugOut()<<"plugin config key: "<<srcMembers[i]<<" value: "<<configurationMap[srcMembers[i]]<<endl;
-                       json_reader_end_member(reader);
+                       string valstr = json_object_get_string(val);
+                       DebugOut() << "plugin config key: " << key << "value:" << valstr << endl;
+                       configurationMap[key] = valstr;
                }
-
-               json_reader_read_member(reader, "path");
-               string path = json_reader_get_string_value(reader);
-               json_reader_end_member(reader);
+               json_object *pathobject = json_object_object_get(obj,"path");
+               string path = string(json_object_get_string(pathobject));
 
                AbstractSource* plugin = loadPlugin<AbstractSource*>(path,configurationMap);
                
@@ -120,34 +114,32 @@ PluginLoader::PluginLoader(string configFile, AbstractRoutingEngine* re, int arg
                {
                        mSources.push_back(plugin);
                }
-
-               json_reader_end_element(reader);
+               json_object_put(pathobject);
        }
-                       
-       json_reader_end_member(reader);
+       array_list_free(sourceslist);
+       json_object_put(sourcesobject);
 
        ///read the sinks:
-               
-       json_reader_read_member(reader,"sinks");
-
-       for(int i=0; i < json_reader_count_elements(reader); i++)
+       
+       json_object *sinksobject = json_object_object_get(rootobject,"sinks");
+       array_list *sinkslist = json_object_get_array(sinksobject);
+       
+       for(int i=0; i < array_list_length(sinkslist); i++)
        {
-               json_reader_read_element(reader,i);
-
-               gchar** srcMembers = json_reader_list_members(reader);
+               json_object *obj = (json_object*)array_list_get_idx(sinkslist,i);
 
                std::map<std::string, std::string> configurationMap;
 
-               for(int i=0; i< json_reader_count_members(reader); i++)
+               json_object_object_foreach(obj, key, val)
                {
-                       json_reader_read_member(reader,srcMembers[i]);
-                       configurationMap[srcMembers[i]] = json_reader_get_string_value(reader);
-                       json_reader_end_member(reader);
+                       string valstr = json_object_get_string(val);
+                       DebugOut() << "plugin config key: " << key << "value:" << valstr << endl;
+                       configurationMap[key] = valstr;
                }
 
-               json_reader_read_member(reader, "path");
-               string path = json_reader_get_string_value(reader);
-               json_reader_end_member(reader);
+               
+               json_object *pathobject = json_object_object_get(obj,"path");
+               string path = string(json_object_get_string(pathobject));
 
                AbstractSinkManager* plugin = loadPlugin<AbstractSinkManager*>(path, configurationMap);
 
@@ -155,19 +147,20 @@ PluginLoader::PluginLoader(string configFile, AbstractRoutingEngine* re, int arg
                {
                        throw std::runtime_error("plugin is not a SinkManager");
                }
+               json_object_put(pathobject);
 
-               json_reader_end_element(reader);
        }
-
-       json_reader_end_member(reader);
+       array_list_free(sinkslist);
+       json_object_put(sinksobject);
+               
        
        ///TODO: this will probably explode:
        
-       if(error) g_error_free(error);
-       
-       g_object_unref(reader);
-       g_object_unref(parser);
+       //if(error) g_error_free(error);
        
+       //g_object_unref(reader);
+       //g_object_unref(parser);
+       //*/
 }
 
 PluginLoader::~PluginLoader()
index 2948d5e..3849cd4 100644 (file)
@@ -5,8 +5,8 @@
 #include "abstractpropertytype.h"
 #include <map>
 #include <debugout.h>
-#include <json-glib/json-glib.h>
-
+//#include <json-glib/json-glib.h>
+#include <json/json.h>
 template <class T, class N>
 class MapPropertyType: public AbstractPropertyType
 {
@@ -50,24 +50,34 @@ public:
 
        void fromString(std::string str)
        {
-               JsonParser* parser = json_parser_new();
-               GError* error = nullptr;
-               if(!json_parser_load_from_data(parser, str.c_str(), str.length(), &error))
+               json_object *rootobject;
+               json_tokener *tokener = json_tokener_new();
+               enum json_tokener_error err;
+               do
+               {
+                       rootobject = json_tokener_parse_ex(tokener, str.c_str(),str.length());
+               } while ((err = json_tokener_get_error(tokener)) == json_tokener_continue);
+               if (err != json_tokener_success)
                {
-                       DebugOut()<<"Failed to load config: "<<error->message;
-                       throw std::runtime_error("Failed to load config");
+                       fprintf(stderr, "Error: %s\n", json_tokener_error_desc(err));
+                       // Handle errors, as appropriate for your application.
                }
+               if (tokener->char_offset < str.length()) // XXX shouldn't access internal fields
+               {
+                       // Handle extra characters after parsed object as desired.
+                       // e.g. issue an error, parse another object from that point, etc...
+               }
+               //Good!
+               
+               json_object_object_foreach(rootobject, key, val)
+               {
+                       T one(key);
+                       N two(json_object_get_string(val));
+                       append(one,two);
 
-               JsonNode* node = json_parser_get_root(parser);
-
-               if(node == nullptr)
-                       throw std::runtime_error("Unable to get JSON root object");
-
-               JsonReader* reader = json_reader_new(node);
-
-               if(reader == nullptr)
-                       throw std::runtime_error("Unable to create JSON reader");
-
+               }
+               json_object_put(rootobject);
+               /*
                DebugOut()<<"Config members: "<<json_reader_count_members(reader)<<endl;
 
                gchar** srcMembers = json_reader_list_members(reader);
@@ -84,7 +94,7 @@ public:
 
                g_free(srcMembers);
                g_object_unref(reader);
-               g_object_unref(parser);
+               g_object_unref(parser);*/
        }
 
        GVariant* toVariant()
index 2f31a18..996b0e1 100644 (file)
 #include "websocketsinkmanager.h"
 #include "websocketsink.h"
 #include <sstream>
-#include <json-glib/json-glib.h>
+//#include <json-glib/json-glib.h>
+#include <json/json.h>
+#include <json/json_object.h>
+#include <json/json_tokener.h>
 #include <listplusplus.h>
 #define __SMALLFILE__ std::string(__FILE__).substr(std::string(__FILE__).rfind("/")+1)
 
@@ -497,96 +500,64 @@ static int websocket_callback(struct libwebsocket_context *context,struct libweb
                        GError* error = nullptr;
 
 
-                       JsonParser* parser = json_parser_new();
-                       if (!json_parser_load_from_data(parser,(char*)in,len,&error))
+                       json_object *rootobject;
+                       json_tokener *tokener = json_tokener_new();
+                       enum json_tokener_error err;
+                       do
                        {
-                               DebugOut() << __SMALLFILE__ <<":"<< __LINE__ << "Error loading JSON\n";
-                               return 0;
-                       }
-
-                       JsonNode* node = json_parser_get_root(parser);
-                       if(node == nullptr)
+                               rootobject = json_tokener_parse_ex(tokener, (char*)in,len);
+                       } while ((err = json_tokener_get_error(tokener)) == json_tokener_continue);
+                       if (err != json_tokener_success)
                        {
-                               DebugOut() << __SMALLFILE__ <<":"<< __LINE__ << "Error getting root node of json\n";
-                               //throw std::runtime_error("Unable to get JSON root object");
-                               return 0;
+                               fprintf(stderr, "Error: %s\n", json_tokener_error_desc(err));
+                               // Handle errors, as appropriate for your application.
                        }
-
-                       JsonReader* reader = json_reader_new(node);
-                       if(reader == nullptr)
+                       if (tokener->char_offset < len) // XXX shouldn't access internal fields
                        {
-                               DebugOut() << __SMALLFILE__ <<":"<< __LINE__ << "json_reader is null!\n";
-                               //throw std::runtime_error("Unable to create JSON reader");
-                               return 0;
+                               // Handle extra characters after parsed object as desired.
+                               // e.g. issue an error, parse another object from that point, etc...
                        }
-
-
-
-
-
-                       string type;
-                       json_reader_read_member(reader,"type");
-                       type = json_reader_get_string_value(reader);
-                       json_reader_end_member(reader);
-
-                       string  name;
-                       json_reader_read_member(reader,"name");
-                       name = json_reader_get_string_value(reader);
-                       json_reader_end_member(reader);
+                       // Success, use jobj here.
+                       json_object *typeobject = json_object_object_get(rootobject,"type");
+                       json_object *nameobject = json_object_object_get(rootobject,"name");
+                       json_object *transidobject = json_object_object_get(rootobject,"transactionid");
                        
+                       string type = string(json_object_get_string(typeobject));
+                       string name = string(json_object_get_string(nameobject));
                        string id;
-                       json_reader_read_member(reader,"transactionid");
-                       if (strcmp("gchararray",g_type_name(json_node_get_value_type(json_reader_get_value(reader)))) == 0)
+                       if (json_object_get_type(transidobject) == json_type_string)
                        {
-                               //Type is a string
-                               id = json_reader_get_string_value(reader);
+                               id = string(json_object_get_string(transidobject));
                        }
                        else
                        {
-                               //Type is an integer
                                stringstream strstr;
-                               strstr << json_reader_get_int_value(reader);
+                               strstr << json_object_get_int(transidobject);
                                id = strstr.str();
                        }
-                       json_reader_end_member(reader);
-
-                       
+                       json_object_put(typeobject);
+                       json_object_put(nameobject);
+                       json_object_put(transidobject);
                        if (type == "method" && name == "getRanged")
                        {
-                               json_reader_read_member(reader,"data");
-                               if (json_reader_is_object(reader))
+                               json_object *dataobject = json_object_object_get(rootobject,"data");
+                               if (json_object_get_type(dataobject) == json_type_object)
                                {
-                                       double timeBegin;
-                                       double timeEnd;
-                                       double sequenceBegin;
-                                       double sequenceEnd;
-                                       string property;
-                                       if (json_reader_read_member(reader,"timeBegin"))
-                                       {
-                                               timeBegin = boost::lexical_cast<double,std::string>(json_reader_get_string_value(reader));
-                                               json_reader_end_member(reader);
-                                       }
-                                       
-                                       if (json_reader_read_member(reader,"timeEnd"))
-                                       {
-                                               timeEnd = boost::lexical_cast<double,std::string>(json_reader_get_string_value(reader));
-                                               json_reader_end_member(reader);
-                                       }
-                                       if (json_reader_read_member(reader,"sequenceBegin"))
-                                       {
-                                               sequenceBegin = boost::lexical_cast<double,std::string>(json_reader_get_string_value(reader));
-                                               json_reader_end_member(reader);
-                                       }
-                                       if (json_reader_read_member(reader,"sequenceEnd"))
-                                       {
-                                               sequenceEnd = boost::lexical_cast<double,std::string>(json_reader_get_string_value(reader));
-                                               json_reader_end_member(reader);
-                                       }
-                                       if (json_reader_read_member(reader,"property"))
-                                       {
-                                               property = json_reader_get_string_value(reader);
-                                               json_reader_end_member(reader);
-                                       }
+                                       json_object *timeBeginObject = json_object_object_get(dataobject,"timeBegin");
+                                       json_object *timeEndObject = json_object_object_get(dataobject,"timeEnd");
+                                       json_object *sequenceBeginObject = json_object_object_get(dataobject,"sequenceBegin");
+                                       json_object *sequenceEndObject = json_object_object_get(dataobject,"sequenceEnd");
+                                       json_object *propertyObject = json_object_object_get(dataobject,"property");
+                                       double timeBegin = boost::lexical_cast<double,std::string>(json_object_get_string(timeBeginObject));
+                                       double timeEnd = boost::lexical_cast<double,std::string>(json_object_get_string(timeEndObject));
+                                       double sequenceBegin = boost::lexical_cast<double,std::string>(json_object_get_string(sequenceBeginObject));
+                                       double sequenceEnd = boost::lexical_cast<double,std::string>(json_object_get_string(sequenceEndObject));
+                                       string property = string(json_object_get_string(propertyObject));
+                                       json_object_put(timeBeginObject);
+                                       json_object_put(timeEndObject);
+                                       json_object_put(sequenceBeginObject);
+                                       json_object_put(sequenceEndObject);
+                                       json_object_put(propertyObject);
                                        if ((timeBegin < 0 && timeEnd > 0) || (timeBegin > 0 && timeEnd < 0))
                                        {
                                                //Invalid time begin/end pair
@@ -597,7 +568,6 @@ static int websocket_callback(struct libwebsocket_context *context,struct libweb
                                        }
                                        sinkManager->addSingleShotRangedSink(wsi,property,timeBegin,timeEnd,sequenceBegin,sequenceEnd,id);
                                }
-                               json_reader_end_member(reader);
                        }
                        else
                        {
@@ -605,43 +575,41 @@ static int websocket_callback(struct libwebsocket_context *context,struct libweb
                                vector<string> data;
                                list<string> key;
                                list<string> value;
-                               json_reader_read_member(reader,"data");
-                               if (json_reader_is_array(reader))
+                               json_object *dataobject = json_object_object_get(rootobject,"data");
+                               if (json_object_get_type(dataobject) == json_type_array)
                                {
-                                       for(int i=0; i < json_reader_count_elements(reader); i++)
+                                       array_list *arraylist = json_object_get_array(dataobject);
+                                       for (int i=0;i<array_list_length(arraylist);i++)
                                        {
-                                               json_reader_read_element(reader,i);
-                                               if (json_reader_is_value(reader))
+                                               json_object *arrayobject = (json_object*)array_list_get_idx(arraylist,i);
+                                               if (json_object_get_type(arrayobject) == json_type_object)
                                                {
-                                                       //Raw string value
-                                                       string path = json_reader_get_string_value(reader);
-                                                       data.push_back(path);
-
-                                               }
-                                               else
-                                               {
-                                                       //Not a raw string value, then it's "property/value" kvp, for "set" requests
-                                                       json_reader_read_member(reader,"property");
-                                                       string keystr = json_reader_get_string_value(reader);
+                                                       json_object *propobject = json_object_object_get(arrayobject,"property");
+                                                       json_object *valueobject = json_object_object_get(arrayobject,"value");
+                                                       string keystr = string(json_object_get_string(propobject));
+                                                       string valuestr = string(json_object_get_string(valueobject));
                                                        key.push_back(keystr);
-                                                       json_reader_end_member(reader);
-                                                       json_reader_read_member(reader,"value");
-                                                       string valuestr = json_reader_get_string_value(reader);
                                                        value.push_back(valuestr);
-                                                       json_reader_end_member(reader);
+                                                       json_object_put(propobject);
+                                                       json_object_put(valueobject);
+                                               }
+                                               else if (json_object_get_type(arrayobject) == json_type_string)
+                                               {
+                                                       string path = string(json_object_get_string(arrayobject));
+                                                       data.push_back(path);
                                                }
-                                               json_reader_end_element(reader);
                                        }
+                                       array_list_free(arraylist);
                                }
                                else
                                {
-                                       string path = json_reader_get_string_value(reader);
+                                       string path = json_object_get_string(dataobject);
                                        if (path != "")
                                        {
                                                data.push_back(path);
                                        }
                                }
-                               json_reader_end_member(reader);
+                               json_object_put(dataobject);
                                if (type == "method")
                                {
                                        if (name == "get")
@@ -767,13 +735,6 @@ static int websocket_callback(struct libwebsocket_context *context,struct libweb
                        }
 
                        
-                       ///TODO: this will probably explode:
-                       //mlc: I agree with Kevron here, it does explode.
-                       //if(error) g_error_free(error);
-
-                       g_object_unref(reader);
-                       g_object_unref(parser);
-
 
                        
                        break;