aboutsummaryrefslogtreecommitdiffstats
path: root/Controler-afb
diff options
context:
space:
mode:
authorfulup <fulup.arfoll@iot.bzh>2017-08-11 19:44:21 +0200
committerfulup <fulup.arfoll@iot.bzh>2017-08-11 19:44:21 +0200
commitb65178642727536972d0c04e53b2310be58beb2e (patch)
treef06f8773ce44f8320e9e86cee60e59e1597d6b78 /Controler-afb
parentc13952824e2cc110b9405e1bc9017801dd938ac0 (diff)
Almost working version with Json Config, Lua script and sharelib callbacks.
Diffstat (limited to 'Controler-afb')
-rw-r--r--Controler-afb/ctl-binding.c6
-rw-r--r--Controler-afb/ctl-binding.h27
-rw-r--r--Controler-afb/ctl-dispatch.c209
-rw-r--r--Controler-afb/ctl-lua.c59
-rw-r--r--Controler-afb/ctl-plugin-sample.c65
5 files changed, 272 insertions, 94 deletions
diff --git a/Controler-afb/ctl-binding.c b/Controler-afb/ctl-binding.c
index fe9388f..dc225a4 100644
--- a/Controler-afb/ctl-binding.c
+++ b/Controler-afb/ctl-binding.c
@@ -31,17 +31,17 @@
PUBLIC void ctlapi_navigation (afb_req request) {
- ctlapi_dispatch (CTLAPI_NAVIGATION, request);
+ ctlapi_dispatch ("NAVIGATION", request);
}
PUBLIC void ctlapi_multimedia (afb_req request) {
- ctlapi_dispatch (CTLAPI_MULTIMEDIA, request);
+ ctlapi_dispatch ("MULTIMEDIA", request);
}
PUBLIC void ctlapi_emergency (afb_req request) {
- ctlapi_dispatch (CTLAPI_EMERGENCY, request);
+ ctlapi_dispatch ("EMERGENCY", request);
}
PUBLIC void ctlapi_monitor (afb_req request) {
diff --git a/Controler-afb/ctl-binding.h b/Controler-afb/ctl-binding.h
index abcb2f4..deef93c 100644
--- a/Controler-afb/ctl-binding.h
+++ b/Controler-afb/ctl-binding.h
@@ -28,6 +28,13 @@
#endif
#define STATIC static
+// sharelib ctl-plugin*
+typedef struct {
+ long magic;
+ char *label;
+} CtlPluginMagicT;
+
+#define CTL_PLUGIN_REGISTER(pluglabel) CtlPluginMagicT CtlPluginMagic={.magic=CTL_PLUGIN_MAGIC,.label=pluglabel}; struct afb_binding_data_v2;
// polctl-binding.c
PUBLIC int CtlBindingInit ();
@@ -44,14 +51,6 @@ PUBLIC void ctlapi_event_test (afb_req request);
// -----------
typedef enum {
- CTLAPI_NAVIGATION,
- CTLAPI_MULTIMEDIA,
- CTLAPI_EMERGENCY,
-
- CTL_NONE=-1
-} DispatchCtlEnumT;
-
-typedef enum {
CTL_SCAN_FLAT=0,
CTL_SCAN_RECURSIVE=1,
} CtlScanDirModeT;
@@ -71,15 +70,23 @@ typedef struct DispatchActionS{
const char* call;
json_object *argsJ;
int timeout;
- json_object* (*actionCB)(struct DispatchActionS *action,json_object *response, void *context);
+ int (*actionCB)(afb_req request, struct DispatchActionS *action, void *context);
} DispatchActionT;
PUBLIC int DispatchInit(void);
-PUBLIC void ctlapi_dispatch (DispatchCtlEnumT control, afb_req request);
+PUBLIC void ctlapi_dispatch (char* control, afb_req request);
// ctl-lua.c
+
+typedef enum {
+ LUA_DOCALL,
+ LUA_DOSTRING,
+ LUA_DOSCRIPT,
+} LuaDoActionT;
+
PUBLIC int LuaLibInit ();
PUBLIC json_object* ScanForConfig (char* searchPath, CtlScanDirModeT mode, char *pre, char *ext);
+PUBLIC int LuaCallFunc (afb_req request, DispatchActionT *action);
PUBLIC void ctlapi_lua_docall (afb_req request);
PUBLIC void ctlapi_lua_dostring (afb_req request);
PUBLIC void ctlapi_lua_doscript (afb_req request);
diff --git a/Controler-afb/ctl-dispatch.c b/Controler-afb/ctl-dispatch.c
index 4fa1844..8fdf46e 100644
--- a/Controler-afb/ctl-dispatch.c
+++ b/Controler-afb/ctl-dispatch.c
@@ -31,7 +31,6 @@ typedef void*(*DispatchPluginInstallCbT)(const char* label, const char*version,
typedef struct {
const char* label;
const char *info;
- const char *version;
DispatchActionT *actions;
} DispatchHandleT;
@@ -44,17 +43,83 @@ typedef struct {
void *dlHandle;
DispatchHandleT *onload;
DispatchHandleT *events;
- DispatchHandleT *controls;
+ DispatchHandleT **controls;
} DispatchConfigT;
-STATIC DispatchConfigT *ctlHandle = NULL;
+// global config handle
+STATIC DispatchConfigT *configHandle = NULL;
-PUBLIC void ctlapi_dispatch (DispatchCtlEnumT control, afb_req request) {
- json_object*tmpJ;
+STATIC int DispatchControlToIndex(char* controlLabel) {
+ DispatchHandleT **controls=configHandle->controls;
+ for (int idx=0; controls[idx]; idx++) {
+ if (!strcasecmp(controlLabel, controls[idx]->label)) return idx;
+ }
+ return 0;
+}
+
+PUBLIC void ctlapi_dispatch (char* controlLabel, afb_req request) {
+ DispatchHandleT **controls=configHandle->controls;
+ int err;
+
+ if(!configHandle->controls) {
+ AFB_ERROR ("DISPATCH-CTL-API: No Control Action in Json config label=%s version=%s", configHandle->label, configHandle->version);
+ goto OnErrorExit;
+ }
- json_object* argsJ= afb_req_json(request);
- int done=json_object_object_get_ex(argsJ, "closing", &tmpJ);
- if (done) return;
+ int index=DispatchControlToIndex(controlLabel);
+ if (!index || !controls[index]->actions) {
+ AFB_ERROR ("DISPATCH-CTL-API:NotFound label=%s index=%d", controlLabel, index);
+ goto OnErrorExit;
+ } else {
+ AFB_NOTICE("DISPATCH-CTL-API:Found Control=%s", controls[index]->label);
+ }
+
+ // loop on action for this control
+ DispatchActionT *actions=controls[index]->actions;
+ for (int idx=0; actions[idx].label; idx++) {
+
+ switch (actions[idx].mode) {
+ case CTL_MODE_API: {
+ json_object *returnJ;
+
+ json_object_get( actions[idx].argsJ); // make sure afb_service_call does not free the argsJ
+ int err = afb_service_call_sync(actions[idx].api, actions[idx].call, actions[idx].argsJ, &returnJ);
+ if (err) {
+ AFB_NOTICE ("DISPATCH-CTL-MODE:Api api=%s verb=%s args=%s", actions[idx].api, actions[idx].call, actions[idx].label);
+ afb_req_fail_f(request, "DISPATCH-CTL-MODE:Api", "label=%s api=%s verb=%s", actions[idx].label, actions[idx].api, actions[idx].call);
+ goto OnErrorExit;
+ }
+ break;
+ }
+
+ case CTL_MODE_LUA:
+ err= LuaCallFunc (request, &actions[idx]);
+ if (err) {
+ afb_req_fail_f(request, "DISPATCH-CTL-MODE:Lua", "func=%s args=%s", actions[idx].call, json_object_get_string(actions[idx].argsJ));
+ goto OnErrorExit;
+ }
+ break;
+
+ case CTL_MODE_CB:
+ err= (*actions[idx].actionCB) (request, &actions[idx], configHandle->context);
+ if (err) {
+ afb_req_fail_f(request, "DISPATCH-CTL-MODE:Cb", "func=%s args=%s", actions[idx].call, json_object_get_string(actions[idx].argsJ));
+ goto OnErrorExit;
+ }
+ break;
+
+ default:
+ AFB_ERROR ("DISPATCH-CTL-API:control=%s action=%s", controls[index]->label, actions[idx].label);
+ afb_req_fail_f(request, "DISPATCH-CTL-MODE:Unknown", "control=%s action=%s", controls[index]->label, actions[idx].label);
+ }
+ }
+
+ // everything when fine
+ afb_req_success(request,NULL,controls[index]->label);
+ return;
+
+ OnErrorExit:
+ return;
}
// List Avaliable Configuration Files
@@ -83,12 +148,12 @@ PUBLIC void ctlapi_config (struct afb_req request) {
}
// unpack individual action object
-STATIC int DispatchLoadOneAction (json_object *actionJ, DispatchActionT *action) {
- char *api, *verb, *callback, *lua;
+STATIC int DispatchLoadOneAction (DispatchConfigT *controlConfig, json_object *actionJ, DispatchActionT *action) {
+ char *api=NULL, *verb=NULL, *callback=NULL, *lua=NULL;
int err, modeCount=0;
- err= wrap_json_unpack(actionJ, "{ss,s?s,s?s,s?o,s?s,s?s,s?s !}"
- , "label",&action->label, "info",&action->info, "callback",&callback, "lua", &lua, "args",&action->argsJ, "api",&api, "verb", &verb);
+ err= wrap_json_unpack(actionJ, "{ss,s?s,s?s,s?s,s?s,s?s,s?o !}"
+ , "label",&action->label, "info",&action->info, "callback",&callback, "lua", &lua, "api",&api, "verb", &verb, "args",&action->argsJ);
if (err) {
AFB_ERROR ("DISPATCH-LOAD-ACTION Missing something label|info|callback|lua|(api+verb)|args in %s", json_object_get_string(actionJ));
goto OnErrorExit;
@@ -107,26 +172,26 @@ STATIC int DispatchLoadOneAction (json_object *actionJ, DispatchActionT *action
modeCount++;
}
- if (callback) {
+ if (callback && controlConfig->dlHandle) {
action->mode = CTL_MODE_CB;
action->call=callback;
modeCount++;
- action->actionCB = dlsym(ctlHandle->dlHandle, callback);
+ action->actionCB = dlsym(controlConfig->dlHandle, callback);
if (!action->actionCB) {
- AFB_ERROR ("DISPATCH-LOAD-ACTION fail to find calbback=%s in %s", callback, ctlHandle->plugin);
+ AFB_ERROR ("DISPATCH-LOAD-ACTION fail to find calbback=%s in %s", callback, controlConfig->plugin);
goto OnErrorExit;
}
}
// make sure at least one mode is selected
if (modeCount == 0) {
- AFB_ERROR ("DISPATCH-LOAD-ACTION Missing something lua|callback|(api+verb) in %s", json_object_get_string(actionJ));
+ AFB_ERROR ("DISPATCH-LOAD-ACTION No Action Selected lua|callback|(api+verb) in %s", json_object_get_string(actionJ));
goto OnErrorExit;
}
if (modeCount > 1) {
- AFB_ERROR ("DISPATCH-LOAD-ACTION ToMany lua|callback|(api+verb) in %s", json_object_get_string(actionJ));
+ AFB_ERROR ("DISPATCH-LOAD-ACTION:ToMany arguments lua|callback|(api+verb) in %s", json_object_get_string(actionJ));
goto OnErrorExit;
}
return 0;
@@ -135,7 +200,7 @@ OnErrorExit:
return -1;
};
-STATIC DispatchActionT *DispatchLoadActions (json_object *actionsJ) {
+STATIC DispatchActionT *DispatchLoadActions (DispatchConfigT *controlConfig, json_object *actionsJ) {
int err;
DispatchActionT *actions;
@@ -146,13 +211,13 @@ STATIC DispatchActionT *DispatchLoadActions (json_object *actionsJ) {
for (int idx=0; idx < count; idx++) {
json_object *actionJ = json_object_array_get_idx(actionsJ, idx);
- err = DispatchLoadOneAction (actionJ, &actions[idx]);
+ err = DispatchLoadOneAction (controlConfig, actionJ, &actions[idx]);
if (err) goto OnErrorExit;
}
} else {
actions = calloc (2, sizeof(DispatchActionT));
- err = DispatchLoadOneAction (actionsJ, &actions[0]);
+ err = DispatchLoadOneAction (controlConfig, actionsJ, &actions[0]);
if (err) goto OnErrorExit;
}
@@ -165,25 +230,28 @@ STATIC DispatchActionT *DispatchLoadActions (json_object *actionsJ) {
STATIC DispatchConfigT *DispatchLoadConfig (const char* filepath) {
- json_object *dispatchConfigJ, *ignoreJ;
+ json_object *controlConfigJ, *ignoreJ;
int err;
// Load JSON file
- dispatchConfigJ= json_object_from_file(filepath);
- if (!dispatchConfigJ) goto OnErrorExit;
+ controlConfigJ= json_object_from_file(filepath);
+ if (!controlConfigJ) {
+ AFB_ERROR ("DISPATCH-LOAD-CONFIG:JsonLoad invalid JSON %s ", filepath);
+ goto OnErrorExit;
+ }
AFB_INFO ("DISPATCH-LOAD-CONFIG: loading config filepath=%s", filepath);
json_object *metadataJ=NULL, *onloadJ=NULL, *controlsJ=NULL, *eventsJ=NULL;
- err= wrap_json_unpack(dispatchConfigJ, "{s?o,so,s?o,s?o,s?o !}", "$schema", &ignoreJ, "metadata",&metadataJ, "onload",&onloadJ, "controls",&controlsJ, "events",&eventsJ);
+ err= wrap_json_unpack(controlConfigJ, "{s?o,so,s?o,s?o,s?o !}", "$schema", &ignoreJ, "metadata",&metadataJ, "onload",&onloadJ, "controls",&controlsJ, "events",&eventsJ);
if (err) {
- AFB_ERROR ("DISPATCH-LOAD-CONFIG Missing something metadata|[onload]|[controls]|[events] in %s", json_object_get_string(dispatchConfigJ));
+ AFB_ERROR ("DISPATCH-LOAD-CONFIG Missing something metadata|[onload]|[controls]|[events] in %s", json_object_get_string(controlConfigJ));
goto OnErrorExit;
}
- DispatchConfigT *dispatchConfig = calloc (1, sizeof(DispatchConfigT));
+ DispatchConfigT *controlConfig = calloc (1, sizeof(DispatchConfigT));
if (metadataJ) {
- err= wrap_json_unpack(metadataJ, "{ss,s?s,ss !}", "label", &dispatchConfig->label, "info",&dispatchConfig->info, "version",&dispatchConfig->version);
+ err= wrap_json_unpack(metadataJ, "{ss,s?s,ss !}", "label", &controlConfig->label, "info",&controlConfig->info, "version",&controlConfig->version);
if (err) {
AFB_ERROR ("DISPATCH-LOAD-CONFIG:METADATA Missing something label|version|[label] in %s", json_object_get_string(metadataJ));
goto OnErrorExit;
@@ -193,19 +261,18 @@ STATIC DispatchConfigT *DispatchLoadConfig (const char* filepath) {
if (onloadJ) {
json_object * actionsJ;
DispatchHandleT *dispatchHandle = calloc (1, sizeof(DispatchHandleT));
-
- err= wrap_json_unpack(onloadJ, "{so,s?s,s?s,s?o !}", "label",&dispatchHandle->label, "info",&dispatchHandle->info, "plugin", &dispatchConfig->plugin, "actions",&actionsJ);
+ err= wrap_json_unpack(onloadJ, "{so,s?s,s?s,s?o !}", "label",&dispatchHandle->label, "info",&dispatchHandle->info, "plugin", &controlConfig->plugin, "actions",&actionsJ);
if (err) {
AFB_ERROR ("DISPATCH-LOAD-CONFIG:ONLOAD Missing something label|[info]|[plugin]|[actions] in %s", json_object_get_string(onloadJ));
goto OnErrorExit;
}
- if (dispatchConfig->plugin) {
+ if (controlConfig->plugin) {
// search for default policy config file
- json_object *pluginPathJ = ScanForConfig(CONTROL_PLUGIN_PATH , CTL_SCAN_RECURSIVE, dispatchConfig->plugin, NULL);
+ json_object *pluginPathJ = ScanForConfig(CONTROL_PLUGIN_PATH , CTL_SCAN_RECURSIVE, controlConfig->plugin, NULL);
if (!pluginPathJ || json_object_array_length(pluginPathJ) == 0) {
- AFB_ERROR ("DISPATCH-LOAD-CONFIG:PLUGIN Missing plugin=%s in path=%s", dispatchConfig->plugin, CONTROL_PLUGIN_PATH);
+ AFB_ERROR ("DISPATCH-LOAD-CONFIG:PLUGIN Missing plugin=%s in path=%s", controlConfig->plugin, CONTROL_PLUGIN_PATH);
goto OnErrorExit;
}
@@ -224,39 +291,67 @@ STATIC DispatchConfigT *DispatchLoadConfig (const char* filepath) {
strncpy(pluginpath, fullpath, sizeof(pluginpath));
strncat(pluginpath, "/", sizeof(pluginpath));
strncat(pluginpath, filename, sizeof(pluginpath));
- dispatchConfig->dlHandle = dlopen(pluginpath, RTLD_NOW);
- if (!dispatchConfig->dlHandle) {
- AFB_ERROR ("DISPATCH-LOAD-CONFIG:PLIUGIN Fail to load pluginpath=%s err= %s", pluginpath, dlerror());
+ controlConfig->dlHandle = dlopen(pluginpath, RTLD_NOW);
+ if (!controlConfig->dlHandle) {
+ AFB_ERROR ("DISPATCH-LOAD-CONFIG:PLUGIN Fail to load pluginpath=%s err= %s", pluginpath, dlerror());
goto OnErrorExit;
}
- ulong *ctlPluginMagic = (ulong*)dlsym(dispatchConfig->dlHandle, "CtlPluginMagic");
- if (!ctlPluginMagic || *ctlPluginMagic != CTL_PLUGIN_MAGIC) {
- AFB_ERROR("DISPATCH-LOAD-CONFIG:PLIUGIN symbol'CtlPluginMagic' missing or != CTL_PLUGIN_MAGIC plugin=%s", pluginpath);
+ CtlPluginMagicT *ctlPluginMagic = (CtlPluginMagicT*)dlsym(controlConfig->dlHandle, "CtlPluginMagic");
+ if (!ctlPluginMagic || ctlPluginMagic->magic != CTL_PLUGIN_MAGIC) {
+ AFB_ERROR("DISPATCH-LOAD-CONFIG:Plugin symbol'CtlPluginMagic' missing or != CTL_PLUGIN_MAGIC plugin=%s", pluginpath);
goto OnErrorExit;
+ } else {
+ AFB_NOTICE("DISPATCH-LOAD-CONFIG:Plugin %s successfully registered", ctlPluginMagic->label);
}
- DispatchPluginInstallCbT ctlPluginInstall = dlsym(dispatchConfig->dlHandle, "CtlPluginOnload");
- if (ctlPluginInstall) {
- dispatchConfig->context = (*ctlPluginInstall) (dispatchConfig->label, dispatchConfig->version, dispatchConfig->info);
+ // Jose hack to make verbosity visible from sharelib
+ struct afb_binding_data_v2 *afbHidenData = dlsym(controlConfig->dlHandle, "afbBindingV2data");
+ if (afbHidenData) *afbHidenData = afbBindingV2data;
+
+ DispatchPluginInstallCbT ctlPluginOnload = dlsym(controlConfig->dlHandle, "CtlPluginOnload");
+ if (ctlPluginOnload) {
+ controlConfig->context = (*ctlPluginOnload) (controlConfig->label, controlConfig->version, controlConfig->info);
}
}
- dispatchHandle->actions= DispatchLoadActions(actionsJ);
- dispatchConfig->onload= dispatchHandle;
+ dispatchHandle->actions= DispatchLoadActions(controlConfig, actionsJ);
+ if (!dispatchHandle->actions) {
+ AFB_ERROR ("DISPATCH-LOAD-CONFIG:ONLOAD Error when parsing actions %s", dispatchHandle->label);
+ goto OnErrorExit;
+ }
+ controlConfig->onload= dispatchHandle;
+
}
if (controlsJ) {
json_object * actionsJ;
- DispatchHandleT *dispatchHandle = calloc (1, sizeof(DispatchHandleT));
- err= wrap_json_unpack(controlsJ, "{so,s?s,so !}", "label",&dispatchHandle->label, "info",&dispatchHandle->info, "actions",&actionsJ);
- if (err) {
- AFB_ERROR ("DISPATCH-LOAD-CONFIG:CONTROLS Missing something label|[info]|actions in %s", json_object_get_string(controlsJ));
- goto OnErrorExit;
+ if (json_object_get_type(controlsJ) != json_type_array) {
+ AFB_ERROR ("DISPATCH-LOAD-CONFIG:CONTROLS invalid JSON array in %s", json_object_get_string(controlsJ));
+ goto OnErrorExit;
+ }
+
+ int length= json_object_array_length(controlsJ);
+ controlConfig->controls = (DispatchHandleT**) calloc (length+1, sizeof(void*));
+
+ for (int jdx=0; jdx< length; jdx++) {
+ DispatchHandleT *dispatchHandle = calloc (1, sizeof(DispatchHandleT));
+ json_object *controlJ = json_object_array_get_idx(controlsJ,jdx);
+ err= wrap_json_unpack(controlJ, "{ss,s?s,so !}", "label",&dispatchHandle->label, "info",&dispatchHandle->info, "actions",&actionsJ);
+ if (err) {
+ AFB_ERROR ("DISPATCH-LOAD-CONFIG:CONTROLS Missing something label|[info]|actions in %s", json_object_get_string(controlJ));
+ goto OnErrorExit;
+ }
+
+ dispatchHandle->actions= DispatchLoadActions(controlConfig, actionsJ);
+ if (!dispatchHandle->actions) {
+ AFB_ERROR ("DISPATCH-LOAD-CONFIG:CONTROLS Error when parsing actions %s", dispatchHandle->label);
+ goto OnErrorExit;
+ }
+ controlConfig->controls[jdx]= dispatchHandle;
}
- dispatchHandle->actions= DispatchLoadActions(actionsJ);
- dispatchConfig->onload= dispatchHandle;
+
}
if (eventsJ) {
@@ -268,11 +363,15 @@ STATIC DispatchConfigT *DispatchLoadConfig (const char* filepath) {
AFB_ERROR ("DISPATCH-LOAD-CONFIG:EVENTS Missing something label|[info]|actions in %s", json_object_get_string(eventsJ));
goto OnErrorExit;
}
- dispatchHandle->actions= DispatchLoadActions(actionsJ);
- dispatchConfig->onload= dispatchHandle;
+ dispatchHandle->actions= DispatchLoadActions(controlConfig, actionsJ);
+ if (!dispatchHandle->actions) {
+ AFB_ERROR ("DISPATCH-LOAD-CONFIG:EVENTS Error when parsing actions %s", dispatchHandle->label);
+ goto OnErrorExit;
+ }
+ controlConfig->events= dispatchHandle;
}
- return dispatchConfig;
+ return controlConfig;
OnErrorExit:
return NULL;
@@ -301,8 +400,8 @@ PUBLIC int DispatchInit () {
strncpy(filepath, fullpath, sizeof(filepath));
strncat(filepath, "/", sizeof(filepath));
strncat(filepath, filename, sizeof(filepath));
- ctlHandle = DispatchLoadConfig (filepath);
- if (!ctlHandle) {
+ configHandle = DispatchLoadConfig (filepath);
+ if (!configHandle) {
AFB_ERROR ("DISPATCH-INIT:ERROR No File to load [%s]", filepath);
goto OnErrorExit;
}
diff --git a/Controler-afb/ctl-lua.c b/Controler-afb/ctl-lua.c
index 38a3d5f..71ef8b0 100644
--- a/Controler-afb/ctl-lua.c
+++ b/Controler-afb/ctl-lua.c
@@ -36,11 +36,6 @@
static lua_State* luaState;
-typedef enum {
- LUA_DOCALL,
- LUA_DOSTRING,
- LUA_DOSCRIPT,
-} LuaDoActionT;
#define CTX_MAGIC 123456789
#define CTX_TOKEN "AFB_ctx"
@@ -191,6 +186,7 @@ STATIC int LuaPushArgument (json_object *arg) {
lua_pushnumber(luaState, json_object_get_double(arg));
break;
default:
+ AFB_ERROR("LuaPushArgument: unsupported Json object type %s", json_object_get_string(arg));
return 0;
}
@@ -454,7 +450,56 @@ STATIC int LuaAfbService(lua_State* luaState) {
// Generated some fake event based on watchdog/counter
-PUBLIC void LuaDoAction (LuaDoActionT action, afb_req request) {
+PUBLIC int LuaCallFunc (afb_req request, DispatchActionT *action) {
+
+ int err, count=0;
+
+ json_object* queryJ = afb_req_json(request);
+ json_object* argsJ = action->argsJ;
+ const char* func = action->call;
+
+ // load function (should exist in CONTROL_PATH_LUA
+ lua_getglobal(luaState, func);
+
+ // Push AFB client context on the stack
+ LuaAfbContextT *afbContext= LuaCtxPush(luaState, request, func);
+ if (!afbContext) goto OnErrorExit;
+
+ // push argsJ on the stack
+ if (json_object_get_type(argsJ) != json_type_array) {
+ count+= LuaPushArgument (argsJ);
+ } else {
+ for (int idx=0; idx<json_object_array_length(argsJ); idx++) {
+ count += LuaPushArgument (json_object_array_get_idx(argsJ, idx));
+ }
+ }
+
+ // push queryJ on the stack
+ if (json_object_get_type(queryJ) != json_type_array) {
+ count+= LuaPushArgument (queryJ);
+ } else {
+ for (int idx=0; idx<json_object_array_length(queryJ); idx++) {
+ count += LuaPushArgument (json_object_array_get_idx(queryJ, idx));
+ }
+ }
+
+ // effectively exec LUA code (afb_reply/fail done later from callback)
+ err=lua_pcall(luaState, count+1, 1, 0);
+ if (err) {
+ AFB_ERROR("LuaCallFunc Fail calling %s error=%s", func, lua_tostring(luaState,-1));
+ goto OnErrorExit;
+ }
+
+ // return LUA script value
+ int rc= (int)lua_tointeger(luaState, -1);
+ return rc;
+
+ OnErrorExit:
+ return -1;
+}
+
+// Generated some fake event based on watchdog/counter
+STATIC void LuaDoAction (LuaDoActionT action, afb_req request) {
int err, count=0;
@@ -581,8 +626,8 @@ PUBLIC void LuaDoAction (LuaDoActionT action, afb_req request) {
AFB_ERROR ("LUA-DO-EXEC:FAIL query=%s err=%s", json_object_get_string(queryJ), lua_tostring(luaState,-1) );
goto OnErrorExit;
}
+
- return;
OnErrorExit:
afb_req_fail(request,"LUA:ERROR", lua_tostring(luaState,-1));
diff --git a/Controler-afb/ctl-plugin-sample.c b/Controler-afb/ctl-plugin-sample.c
index f7665f0..ebcaee4 100644
--- a/Controler-afb/ctl-plugin-sample.c
+++ b/Controler-afb/ctl-plugin-sample.c
@@ -31,19 +31,8 @@ typedef struct {
int count;
} MyPluginCtxT;
-// This tag is mandotory and used as sanity check when loading plugin
-PUBLIC ulong CtlPluginMagic=CTL_PLUGIN_MAGIC;
-
-// Call at initialisation time
-PUBLIC void* CtlPluginOnload(char* label, char* version, char* info) {
- MyPluginCtxT *pluginCtx= (MyPluginCtxT*)calloc (1, sizeof(MyPluginCtxT));
- pluginCtx->magic = MY_PLUGIN_MAGIC;
- pluginCtx->count = 0;
-
- fprintf(stderr, "*** CONTROLER-PLUGIN-SAMPLE:Install label=%s version=%s info=%s", label, info, version);
- AFB_NOTICE ("CONTROLER-PLUGIN-SAMPLE:Install label=%s version=%s info=%s", label, info, version);
- return (void*)pluginCtx;
-}
+// Declare this sharelib as a Controller Plugin
+CTL_PLUGIN_REGISTER("MyCtlSamplePlugin");
STATIC const char* jsonToString (json_object *valueJ) {
const char *value;
@@ -55,18 +44,56 @@ STATIC const char* jsonToString (json_object *valueJ) {
return value;
}
+// Call at initialisation time
+PUBLIC void* CtlPluginOnload(char* label, char* version, char* info) {
+ MyPluginCtxT *pluginCtx= (MyPluginCtxT*)calloc (1, sizeof(MyPluginCtxT));
+ pluginCtx->magic = MY_PLUGIN_MAGIC;
+ pluginCtx->count = -1;
-PUBLIC void SamplePolicyCount (afb_req request, DispatchActionT *action, void *context) {
-
+ AFB_NOTICE ("CONTROLER-PLUGIN-SAMPLE:Onload label=%s version=%s info=%s", label, info, version);
+ return (void*)pluginCtx;
+}
+
+PUBLIC int SamplePolicyInit (afb_req request, DispatchActionT *action, void *context) {
+ MyPluginCtxT *pluginCtx= (MyPluginCtxT*)context;
+
+ pluginCtx->count = 0;
+ AFB_NOTICE ("CONTROLER-PLUGIN-SAMPLE:Init label=%s args=%s\n", action->label, jsonToString(action->argsJ));
+ return 0;
+}
+
+PUBLIC int sampleControlMultimedia (afb_req request, DispatchActionT *action, void *context) {
MyPluginCtxT *pluginCtx= (MyPluginCtxT*)context;
if (!context || pluginCtx->magic != MY_PLUGIN_MAGIC) {
- AFB_ERROR("CONTROLER-PLUGIN-SAMPLE:count (Hoops) Invalid Sample Plugin Context");
- return;
-
+ AFB_ERROR("CONTROLER-PLUGIN-SAMPLE:sampleControlMultimedia (Hoops) Invalid Sample Plugin Context");
+ return -1;
};
+ pluginCtx->count++;
+ AFB_NOTICE ("CONTROLER-PLUGIN-SAMPLE:sampleControlMultimedia SamplePolicyCount action=%s args=%s count=%d", action->label, jsonToString(action->argsJ), pluginCtx->count);
+ return 0;
+}
+
+PUBLIC int sampleControlNavigation (afb_req request, DispatchActionT *action, void *context) {
+ MyPluginCtxT *pluginCtx= (MyPluginCtxT*)context;
+ if (!context || pluginCtx->magic != MY_PLUGIN_MAGIC) {
+ AFB_ERROR("CONTROLER-PLUGIN-SAMPLE:sampleControlNavigation (Hoops) Invalid Sample Plugin Context");
+ return -1;
+ };
pluginCtx->count++;
+ AFB_NOTICE ("CONTROLER-PLUGIN-SAMPLE:sampleControlNavigation SamplePolicyCount action=%s args=%s count=%d", action->label, jsonToString(action->argsJ), pluginCtx->count);
+ return 0;
+}
- AFB_INFO ("CONTROLER-PLUGIN-SAMPLE:Count SamplePolicyCount action=%s args=%s count=%d", action->label, jsonToString(action->argsJ), pluginCtx->count);
+PUBLIC int SampleControlEvent (afb_req request, DispatchActionT *action, void *context) {
+ MyPluginCtxT *pluginCtx= (MyPluginCtxT*)context;
+
+ if (!context || pluginCtx->magic != MY_PLUGIN_MAGIC) {
+ AFB_ERROR("CONTROLER-PLUGIN-SAMPLE:cousampleControlMultimediant (Hoops) Invalid Sample Plugin Context");
+ return -1;
+ };
+ pluginCtx->count++;
+ AFB_NOTICE ("CONTROLER-PLUGIN-SAMPLE:sampleControlMultimedia SamplePolicyCount action=%s args=%s count=%d", action->label, jsonToString(action->argsJ), pluginCtx->count);
+ return 0;
}