api: started to add idnode to the new API structure
This commit is contained in:
parent
0efeda1727
commit
f067952fd5
6 changed files with 248 additions and 15 deletions
3
Makefile
3
Makefile
|
@ -111,6 +111,7 @@ SRCS = src/version.c \
|
|||
|
||||
SRCS += \
|
||||
src/api.c \
|
||||
src/api/api_idnode.c \
|
||||
|
||||
SRCS += \
|
||||
src/parsers/parsers.c \
|
||||
|
@ -139,7 +140,7 @@ SRCS += src/webui/webui.c \
|
|||
src/webui/simpleui.c \
|
||||
src/webui/statedump.c \
|
||||
src/webui/html.c\
|
||||
src/webui/api.c\
|
||||
src/webui/webui_api.c\
|
||||
|
||||
SRCS += src/muxer.c \
|
||||
src/muxer/muxer_pass.c \
|
||||
|
|
29
src/api.c
29
src/api.c
|
@ -37,18 +37,24 @@ static int ah_cmp
|
|||
}
|
||||
|
||||
void
|
||||
api_register ( const api_hook_t *hooks )
|
||||
api_register ( const api_hook_t *hook )
|
||||
{
|
||||
static api_link_t *t, *skel = NULL;
|
||||
if (!skel)
|
||||
skel = calloc(1, sizeof(api_link_t));
|
||||
skel->hook = hook;
|
||||
t = RB_INSERT_SORTED(&api_hook_tree, skel, link, ah_cmp);
|
||||
if (t)
|
||||
tvherror("api", "trying to re-register subsystem");
|
||||
else
|
||||
skel = NULL;
|
||||
}
|
||||
|
||||
void
|
||||
api_register_all ( const api_hook_t *hooks )
|
||||
{
|
||||
while (hooks->ah_subsystem) {
|
||||
if (!skel)
|
||||
skel = calloc(1, sizeof(api_link_t));
|
||||
skel->hook = hooks;
|
||||
t = RB_INSERT_SORTED(&api_hook_tree, skel, link, ah_cmp);
|
||||
if (t)
|
||||
tvherror("api", "trying to re-register subsystem");
|
||||
else
|
||||
skel = NULL;
|
||||
api_register(hooks);
|
||||
hooks++;
|
||||
}
|
||||
}
|
||||
|
@ -106,5 +112,8 @@ void api_init ( void )
|
|||
{ "serverinfo", ACCESS_ANONYMOUS, api_serverinfo, NULL },
|
||||
{ NULL, 0, NULL, NULL }
|
||||
};
|
||||
api_register(h);
|
||||
api_register_all(h);
|
||||
|
||||
/* Subsystems */
|
||||
api_idnode_init();
|
||||
}
|
||||
|
|
12
src/api.h
12
src/api.h
|
@ -21,6 +21,7 @@
|
|||
#define __TVH_API_H__
|
||||
|
||||
#include "htsmsg.h"
|
||||
#include "idnode.h"
|
||||
#include "redblack.h"
|
||||
|
||||
#define TVH_API_VERSION 12
|
||||
|
@ -43,7 +44,8 @@ typedef struct api_hook
|
|||
/*
|
||||
* Regsiter handler
|
||||
*/
|
||||
void api_register ( const api_hook_t *hooks );
|
||||
void api_register ( const api_hook_t *hook );
|
||||
void api_register_all ( const api_hook_t *hooks );
|
||||
|
||||
/*
|
||||
* Execute
|
||||
|
@ -54,5 +56,13 @@ int api_exec ( const char *subsystem, htsmsg_t *args, htsmsg_t **resp );
|
|||
* Initialise
|
||||
*/
|
||||
void api_init ( void );
|
||||
void api_idnode_init ( void );
|
||||
|
||||
/*
|
||||
* Re-usable functions
|
||||
*/
|
||||
int api_idnode_tree0
|
||||
( const char *uuid, const char *root, idnode_set_t *(*rootfn)(void),
|
||||
htsmsg_t **resp );
|
||||
|
||||
#endif /* __TVH_API_H__ */
|
||||
|
|
204
src/api/api_idnode.c
Normal file
204
src/api/api_idnode.c
Normal file
|
@ -0,0 +1,204 @@
|
|||
/*
|
||||
* API - idnode related API calls
|
||||
*
|
||||
* Copyright (C) 2013 Adam Sutton
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef __TVH_API_IDNODE_H__
|
||||
#define __TVH_API_IDNODE_H__
|
||||
|
||||
#include "tvheadend.h"
|
||||
#include "access.h"
|
||||
#include "idnode.h"
|
||||
#include "htsmsg.h"
|
||||
#include "api.h"
|
||||
|
||||
int
|
||||
api_idnode_tree0
|
||||
( const char *uuid, const char *root,
|
||||
idnode_set_t *(*rootfn)(void), htsmsg_t **resp )
|
||||
{
|
||||
int isroot;
|
||||
idnode_t *node = NULL;
|
||||
|
||||
/* Validate */
|
||||
if (!uuid)
|
||||
return EINVAL;
|
||||
isroot = !strcmp("root", uuid);
|
||||
if (isroot && !(root || rootfn))
|
||||
return EINVAL;
|
||||
|
||||
pthread_mutex_lock(&global_lock);
|
||||
|
||||
if (!isroot || root) {
|
||||
if (!(node = idnode_find(isroot ? root : uuid, NULL))) {
|
||||
pthread_mutex_unlock(&global_lock);
|
||||
return EINVAL;
|
||||
}
|
||||
}
|
||||
|
||||
*resp = htsmsg_create_list();
|
||||
|
||||
/* Root node */
|
||||
if (isroot && node) {
|
||||
htsmsg_t *m = idnode_serialize(node);
|
||||
htsmsg_add_u32(m, "leaf", idnode_is_leaf(node));
|
||||
htsmsg_add_msg(*resp, NULL, m);
|
||||
|
||||
/* Children */
|
||||
} else {
|
||||
idnode_set_t *v = node ? idnode_get_childs(node) : rootfn();
|
||||
if (v) {
|
||||
int i;
|
||||
for(i = 0; i < v->is_count; i++) {
|
||||
htsmsg_t *m = idnode_serialize(v->is_array[i]);
|
||||
htsmsg_add_u32(m, "leaf", idnode_is_leaf(v->is_array[i]));
|
||||
htsmsg_add_msg(*resp, NULL, m);
|
||||
}
|
||||
idnode_set_free(v);
|
||||
}
|
||||
}
|
||||
pthread_mutex_unlock(&global_lock);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
api_idnode_class
|
||||
( const char *class, htsmsg_t *args, htsmsg_t **resp )
|
||||
{
|
||||
int i, brief;
|
||||
const idclass_t *idc;
|
||||
idnode_set_t *is;
|
||||
idnode_t *in;
|
||||
htsmsg_t *e;
|
||||
|
||||
// TODO: this only works if pass as integer
|
||||
brief = htsmsg_get_bool_or_default(args, "brief", 0);
|
||||
|
||||
pthread_mutex_lock(&global_lock);
|
||||
|
||||
/* Find class */
|
||||
if (!(idc = idclass_find(class))) {
|
||||
pthread_mutex_unlock(&global_lock);
|
||||
return EINVAL;
|
||||
}
|
||||
|
||||
*resp = htsmsg_create_list();
|
||||
if ((is = idnode_find_all(idc))) {
|
||||
for (i = 0; i < is->is_count; i++) {
|
||||
in = is->is_array[i];
|
||||
|
||||
/* Name/UUID only */
|
||||
if (brief) {
|
||||
e = htsmsg_create_map();
|
||||
htsmsg_add_str(e, "key", idnode_uuid_as_str(in));
|
||||
htsmsg_add_str(e, "val", idnode_get_title(in));
|
||||
|
||||
/* Full record */
|
||||
} else
|
||||
e = idnode_serialize(in);
|
||||
|
||||
if (e)
|
||||
htsmsg_add_msg(*resp, NULL, e);
|
||||
}
|
||||
}
|
||||
|
||||
pthread_mutex_unlock(&global_lock);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
api_idnode_load
|
||||
( void *opaque, const char *op, htsmsg_t *args, htsmsg_t **resp )
|
||||
{
|
||||
int err = 0;
|
||||
idnode_t *in;
|
||||
htsmsg_t *l;
|
||||
htsmsg_field_t *f;
|
||||
const char *uuid, *class;
|
||||
|
||||
/* Class based */
|
||||
if ((class = htsmsg_get_str(args, "class")))
|
||||
return api_idnode_class(class, args, resp);
|
||||
|
||||
/* ID based */
|
||||
if (!(f = htsmsg_field_find(args, "uuid")))
|
||||
return EINVAL;
|
||||
|
||||
pthread_mutex_lock(&global_lock);
|
||||
|
||||
/* Single */
|
||||
if (f->hmf_type == HMF_STR) {
|
||||
uuid = htsmsg_field_get_string(f);
|
||||
in = idnode_find(uuid, NULL);
|
||||
if (in)
|
||||
*resp = idnode_serialize(in);
|
||||
else
|
||||
err = ENOENT;
|
||||
|
||||
/* Multiple */
|
||||
} else if (f->hmf_type == HMF_LIST) {
|
||||
l = htsmsg_get_list_by_field(f);
|
||||
*resp = htsmsg_create_list();
|
||||
HTSMSG_FOREACH(f, l) {
|
||||
if (!(uuid = htsmsg_field_get_string(f))) continue;
|
||||
if (!(in = idnode_find(uuid, NULL))) continue;
|
||||
htsmsg_add_msg(*resp, NULL, idnode_serialize(in));
|
||||
}
|
||||
|
||||
/* Invalid */
|
||||
} else {
|
||||
err = EINVAL;
|
||||
}
|
||||
|
||||
pthread_mutex_unlock(&global_lock);
|
||||
|
||||
return err;
|
||||
}
|
||||
|
||||
static int
|
||||
api_idnode_save
|
||||
( void *opaque, const char *op, htsmsg_t *args, htsmsg_t **resp )
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
api_idnode_tree
|
||||
( void *opaque, const char *op, htsmsg_t *args, htsmsg_t **resp )
|
||||
{
|
||||
const char *uuid = htsmsg_get_str(args, "uuid");
|
||||
const char *root = htsmsg_get_str(args, "root");
|
||||
|
||||
return api_idnode_tree0(uuid, root, NULL, resp);
|
||||
}
|
||||
|
||||
void api_idnode_init ( void )
|
||||
{
|
||||
static api_hook_t ah[] = {
|
||||
{ "idnode/load", ACCESS_ANONYMOUS, api_idnode_load, NULL },
|
||||
{ "idnode/save", ACCESS_ADMIN, api_idnode_save, NULL },
|
||||
{ "idnode/tree", ACCESS_ANONYMOUS, api_idnode_tree, NULL },
|
||||
{ NULL },
|
||||
};
|
||||
|
||||
api_register_all(ah);
|
||||
}
|
||||
|
||||
|
||||
#endif /* __TVH_API_IDNODE_H__ */
|
|
@ -2223,7 +2223,7 @@ extjs_start(void)
|
|||
|
||||
http_path_add("/tvadapters",
|
||||
NULL, extjs_tvadapters, ACCESS_ADMIN);
|
||||
http_path_add("/api/idnode", NULL, extjs_idnode, ACCESS_ADMIN); // TODO: might want diff access for read/write`
|
||||
http_path_add("/api/idnode2", NULL, extjs_idnode, ACCESS_ADMIN); // TODO: might want diff access for read/write`
|
||||
http_path_add("/api/service_mapping", NULL, extjs_service_mapping, ACCESS_ADMIN);
|
||||
|
||||
extjs_start_dvb();
|
||||
|
|
|
@ -30,15 +30,15 @@ webui_api_handler
|
|||
( http_connection_t *hc, const char *remain, void *opaque )
|
||||
{
|
||||
int r;
|
||||
http_arg_t *ha;
|
||||
htsmsg_t *args, *resp;
|
||||
const char *a = http_arg_get(&hc->hc_req_args, "args");
|
||||
const char *op = http_arg_get(&hc->hc_req_args, "method");
|
||||
|
||||
|
||||
// Compat
|
||||
if (!op)
|
||||
op = http_arg_get(&hc->hc_req_args, "op");
|
||||
|
||||
|
||||
/* Parse arguments */
|
||||
if (a)
|
||||
args = htsmsg_json_deserialize(a);
|
||||
|
@ -47,6 +47,15 @@ webui_api_handler
|
|||
if (!args)
|
||||
return HTTP_STATUS_BAD_REQUEST;
|
||||
|
||||
/* Add HTTP arguments?? */
|
||||
TAILQ_FOREACH(ha, &hc->hc_req_args, link) {
|
||||
// Ignore obvious keys
|
||||
if (strcmp("op", ha->key) &&
|
||||
strcmp("method", ha->key) &&
|
||||
strcmp("args", ha->key))
|
||||
htsmsg_add_str(args, ha->key, ha->val);
|
||||
}
|
||||
|
||||
/* Add operation */
|
||||
if (!htsmsg_get_str(args, "method") && op)
|
||||
htsmsg_add_str(args, "method", op);
|
Loading…
Add table
Reference in a new issue