]> git.ipfire.org Git - thirdparty/freeswitch.git/commitdiff
FS-9896 [mod_v8] Implement Serving Configuration with JavaScript
authorAndrey Volk <andywolk@gmail.com>
Thu, 29 Dec 2016 00:58:22 +0000 (03:58 +0300)
committerAndrey Volk <andywolk@gmail.com>
Thu, 29 Dec 2016 00:58:22 +0000 (03:58 +0300)
conf/curl/autoload_configs/v8.conf.xml
conf/insideout/autoload_configs/v8.conf.xml
conf/vanilla/autoload_configs/v8.conf.xml
src/mod/languages/mod_v8/conf/autoload_configs/v8.conf.xml
src/mod/languages/mod_v8/mod_v8.cpp
src/mod/languages/mod_v8/mod_v8.h

index 01c9e2bd9920fdad3cfd5cf20e8e3436e4aff78a..df0fddd5a35799d2f2ebf32b5e7c7b4fbf8731cd 100644 (file)
@@ -1,4 +1,8 @@
 <configuration name="v8.conf" description="Google V8 JavaScript Plug-Ins">
+  <settings>
+    <!-- <param name="xml-handler-script" value="directory.js"/> -->
+    <!-- <param name="xml-handler-bindings" value="directory"/> -->
+  </settings>
   <modules>
     <!-- <load module="mod_v8_skel"/> -->
   </modules>
index 01c9e2bd9920fdad3cfd5cf20e8e3436e4aff78a..df0fddd5a35799d2f2ebf32b5e7c7b4fbf8731cd 100644 (file)
@@ -1,4 +1,8 @@
 <configuration name="v8.conf" description="Google V8 JavaScript Plug-Ins">
+  <settings>
+    <!-- <param name="xml-handler-script" value="directory.js"/> -->
+    <!-- <param name="xml-handler-bindings" value="directory"/> -->
+  </settings>
   <modules>
     <!-- <load module="mod_v8_skel"/> -->
   </modules>
index 01c9e2bd9920fdad3cfd5cf20e8e3436e4aff78a..df0fddd5a35799d2f2ebf32b5e7c7b4fbf8731cd 100644 (file)
@@ -1,4 +1,8 @@
 <configuration name="v8.conf" description="Google V8 JavaScript Plug-Ins">
+  <settings>
+    <!-- <param name="xml-handler-script" value="directory.js"/> -->
+    <!-- <param name="xml-handler-bindings" value="directory"/> -->
+  </settings>
   <modules>
     <!-- <load module="mod_v8_skel"/> -->
   </modules>
index 01c9e2bd9920fdad3cfd5cf20e8e3436e4aff78a..df0fddd5a35799d2f2ebf32b5e7c7b4fbf8731cd 100644 (file)
@@ -1,4 +1,8 @@
 <configuration name="v8.conf" description="Google V8 JavaScript Plug-Ins">
+  <settings>
+    <!-- <param name="xml-handler-script" value="directory.js"/> -->
+    <!-- <param name="xml-handler-bindings" value="directory"/> -->
+  </settings>
   <modules>
     <!-- <load module="mod_v8_skel"/> -->
   </modules>
index 955a94bd46aa97486b80ab6c239014265490b785..b9cc9b8a5d448b208825c7dacdda4f908cfedfb0 100644 (file)
@@ -25,6 +25,7 @@
  * Peter Olsson <peter@olssononline.se>
  * Anthony Minessale II <anthm@freeswitch.org>
  * William King <william.king@quentustech.com>
+ * Andrey Volk <andywolk@gmail.com>
  *
  * mod_v8.cpp -- JavaScript FreeSWITCH module
  *
@@ -35,6 +36,7 @@
  *
  * It extends the available JavaScript classes with the following FS related classes;
  * CoreDB              Adds features to access the core DB (SQLite) in FreeSWITCH. (on request only)
+ * DBH                 Database Handler. Makes use of connection pooling provided by FreeSWITCH. (on request only)
  * CURL                        Adds some extra methods for CURL access. (on request only)
  * DTMF                        Object that holds information about a DTMF event.
  * Event               Object that holds information about a FreeSWITCH event.
@@ -117,6 +119,7 @@ typedef struct {
        switch_mutex_t *event_mutex;
        switch_event_node_t *event_node;
        set<FSEventHandler *> *event_handlers;
+       char *xml_handler;
 } mod_v8_global_t;
 
 mod_v8_global_t globals = { 0 };
@@ -273,7 +276,24 @@ static switch_status_t load_modules(void)
        switch_core_hash_init(&module_manager.load_hash);
 
        if ((xml = switch_xml_open_cfg(cf, &cfg, NULL))) {
-               switch_xml_t mods, ld;
+               switch_xml_t mods, ld, settings, param;
+
+               if ((settings = switch_xml_child(cfg, "settings"))) {
+                       for (param = switch_xml_child(settings, "param"); param; param = param->next) {
+                               char *var = (char *)switch_xml_attr_soft(param, "name");
+                               char *val = (char *)switch_xml_attr_soft(param, "value");
+
+                               if (!strcmp(var, "xml-handler-script")) {
+                                       globals.xml_handler = switch_core_strdup(globals.pool, val);
+                               }
+                               else if (!strcmp(var, "xml-handler-bindings")) {
+                                       if (!zstr(globals.xml_handler)) {
+                                               switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_INFO, "binding '%s' to '%s'\n", globals.xml_handler, val);
+                                               switch_xml_bind_search_function(v8_fetch, switch_xml_parse_section_string(val), NULL);
+                                       }
+                               }
+                       }
+               }
 
                if ((mods = switch_xml_child(cfg, "modules"))) {
                        for (ld = switch_xml_child(mods, "load"); ld; ld = ld->next) {
@@ -383,7 +403,7 @@ static char *v8_get_script_path(const char *script_file)
        }
 }
 
-static int v8_parse_and_execute(switch_core_session_t *session, const char *input_code, switch_stream_handle_t *api_stream, switch_event_t *message)
+static int v8_parse_and_execute(switch_core_session_t *session, const char *input_code, switch_stream_handle_t *api_stream, switch_event_t *message, v8_xml_handler_t* xml_handler)
 {
        string res;
        JSMain *js;
@@ -502,6 +522,24 @@ static int v8_parse_and_execute(switch_core_session_t *session, const char *inpu
                                                ptr->RegisterInstance(isolate, "request", true);
                                        }
 
+                                       if (xml_handler)
+                                       {
+                                               /* Add xml handler global variables */
+
+                                               Handle<Array> XML_REQUEST = Array::New(isolate, 4);
+                                               
+                                               XML_REQUEST->Set(String::NewFromUtf8(isolate, "key_name"), String::NewFromUtf8(isolate, js_safe_str(xml_handler->key_name)));
+                                               XML_REQUEST->Set(String::NewFromUtf8(isolate, "key_value"), String::NewFromUtf8(isolate, js_safe_str(xml_handler->key_value)));
+                                               XML_REQUEST->Set(String::NewFromUtf8(isolate, "section"), String::NewFromUtf8(isolate, js_safe_str(xml_handler->section)));
+                                               XML_REQUEST->Set(String::NewFromUtf8(isolate, "tag_name"), String::NewFromUtf8(isolate, js_safe_str(xml_handler->tag_name)));
+
+                                               context->Global()->Set(String::NewFromUtf8(isolate, "XML_REQUEST"), XML_REQUEST);
+
+                                               if (xml_handler->params) {
+                                                       FSEvent::New(xml_handler->params, "params", js);
+                                               }
+                                       }
+
                                        script = input_code;
 
                                        if (*script != '~') {
@@ -589,6 +627,16 @@ static int v8_parse_and_execute(switch_core_session_t *session, const char *inpu
                                                                                res = *ascii;
                                                                        }
                                                                }
+
+                                                               if (xml_handler)
+                                                               {                                                                       
+                                                                       Local<Value> value = context->Global()->Get(String::NewFromUtf8(isolate, "XML_STRING"));
+                                                                       String::Utf8Value str(value);
+                                                                       if (strcmp(js_safe_str(*str), "undefined"))
+                                                                       {
+                                                                               xml_handler->XML_STRING = strdup(js_safe_str(*str));
+                                                                       }
+                                                               }
                                                        }
                                                }
 
@@ -635,16 +683,57 @@ static int v8_parse_and_execute(switch_core_session_t *session, const char *inpu
        return result;
 }
 
+static switch_xml_t v8_fetch(const char *section,
+       const char *tag_name, const char *key_name, const char *key_value, switch_event_t *params, void *user_data)
+{
+       switch_xml_t xml = NULL;
+       char *mycmd = NULL;
+
+       if (!zstr(globals.xml_handler)) {
+
+               mycmd = strdup(globals.xml_handler);
+               switch_assert(mycmd);
+
+               v8_xml_handler_t xml_handler;
+               xml_handler.section = section;
+               xml_handler.tag_name = tag_name;
+               xml_handler.key_name = key_name;
+               xml_handler.key_value = key_value;
+               xml_handler.params = params;
+               xml_handler.user_data = user_data;
+               xml_handler.XML_STRING = NULL; //Init as NULL. A script's global var XML_STRING will be duplicated to it!
+
+               v8_parse_and_execute(NULL, mycmd, NULL, NULL, &xml_handler);
+
+               if (xml_handler.XML_STRING) {
+                       if (zstr(xml_handler.XML_STRING)) {
+                               switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "No Result\n");
+                       }
+                       else if (!(xml = switch_xml_parse_str_dynamic(xml_handler.XML_STRING, SWITCH_TRUE))) {                          
+                               switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Error Parsing XML Result!\n");
+                       }
+               }
+
+               // Don't forget to free XML_STRING
+               switch_safe_free(xml_handler.XML_STRING);
+               
+       }
+       
+       switch_safe_free(mycmd);
+
+       return xml;
+}
+
 SWITCH_BEGIN_EXTERN_C
 
 SWITCH_STANDARD_APP(v8_dp_function)
 {
-       v8_parse_and_execute(session, data, NULL, NULL);
+       v8_parse_and_execute(session, data, NULL, NULL, NULL);
 }
 
 SWITCH_STANDARD_CHAT_APP(v8_chat_function)
 {
-       v8_parse_and_execute(NULL, data, NULL, message);
+       v8_parse_and_execute(NULL, data, NULL, message, NULL);
 
        return SWITCH_STATUS_SUCCESS;
 }
@@ -661,7 +750,7 @@ static void *SWITCH_THREAD_FUNC v8_thread_run(switch_thread_t *thread, void *obj
        v8_task_t *task = (v8_task_t *) obj;
        switch_memory_pool_t *pool;
 
-       v8_parse_and_execute(NULL, task->code, NULL, NULL);
+       v8_parse_and_execute(NULL, task->code, NULL, NULL, NULL);
 
        if ((pool = task->pool)) {
                switch_core_destroy_memory_pool(&pool);
@@ -761,7 +850,7 @@ SWITCH_STANDARD_API(jsapi_function)
                return SWITCH_STATUS_SUCCESS;
        }
 
-       v8_parse_and_execute(session, (char *) cmd, stream, NULL);
+       v8_parse_and_execute(session, (char *) cmd, stream, NULL, NULL);
 
        return SWITCH_STATUS_SUCCESS;
 }
@@ -788,7 +877,7 @@ SWITCH_STANDARD_JSON_API(json_function)
        switch_event_add_header_string(stream.param_event, SWITCH_STACK_BOTTOM, "JSON", json_text);
        switch_safe_free(json_text);
 
-       v8_parse_and_execute(session, (char *) path->valuestring, &stream, NULL);
+       v8_parse_and_execute(session, (char *) path->valuestring, &stream, NULL, NULL);
        
        *json_reply = cJSON_Parse((char *)stream.data);
 
index e40d6d27c87797897f907dd86a4c7561217c8ec0..1f97795036ec34c0a6ebec4896127e81e50b34d7 100644 (file)
@@ -60,10 +60,23 @@ typedef struct {
 
 extern module_manager_t module_manager;
 
+/* Struct that stores XML handler information */
+typedef struct {
+       const char *section;
+       const char *tag_name;
+       const char *key_name;
+       const char *key_value;
+       switch_event_t *params;
+       void *user_data;
+       char* XML_STRING;
+} v8_xml_handler_t;
+
 SWITCH_END_EXTERN_C
 
 void v8_add_event_handler(void *event_handler);
 void v8_remove_event_handler(void *event_handler);
+static switch_xml_t v8_fetch(const char *section,
+       const char *tag_name, const char *key_name, const char *key_value, switch_event_t *params, void *user_data);
 
 #endif /* MOD_V8_H */