2018-08-30 Fred Gleason <fredg@paravelsystems.com>

* Integrated the 'Rivendell-C-API'
	[from https://github.com/RadioFreeAsia/rivendell-c-api] in
	'apis/rivwebcapi/'.
	* Added a 'rivendell-webapi' RPM subpackage.
This commit is contained in:
Fred Gleason
2018-08-30 14:06:12 -04:00
parent 28a43eeae2
commit 6a71c397a2
157 changed files with 27894 additions and 16 deletions

View File

@@ -0,0 +1,115 @@
## Makefile.am
##
## (C) Copyright 2015-2018 Fred Gleason <fredg@paravelsystems.com>
##
## This program is free software; you can redistribute it and/or modify
## it under the terms of the GNU General Public License version 2 as
## published by the Free Software Foundation.
##
## 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, write to the Free Software
## Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
##
##
## Use automake to process this into a Makefile.in
AM_CFLAGS = -I$(top_srcdir)/apis/rivwebcapi
lib_LTLIBRARIES = librivwebcapi.la
dist_librivwebcapi_la_SOURCES = rd_addcart.c rd_addcart.h \
rd_addcut.c rd_addcut.h \
rd_addlog.c rd_addlog.h \
rd_assignschedcode.c rd_assignschedcode.h\
rd_audioinfo.c rd_audioinfo.h \
rd_audiostore.c rd_audiostore.h \
rd_common.c rd_common.h \
rd_copyaudio.c rd_copyaudio.h \
rd_createticket.c rd_createticket.h \
rd_deleteaudio.c rd_deleteaudio.h \
rd_deletelog.c rd_deletelog.h \
rd_editcart.c rd_editcart.h \
rd_editcut.c rd_editcut.h \
rd_export.c rd_export.h \
rd_exportpeaks.c rd_exportpeaks.h \
rd_getuseragent.c rd_getuseragent.h \
rd_getversion.c rd_getversion.h \
rd_import.c rd_import.h \
rd_listcartschedcodes.c rd_listcartschedcodes.h\
rd_listcart.c rd_listcart.h \
rd_listcarts.c rd_listcarts.h \
rd_listcut.c rd_listcut.h \
rd_listcuts.c rd_listcuts.h \
rd_listgroups.c rd_listgroups.h \
rd_listgroup.c rd_listgroup.h \
rd_listlog.c rd_listlog.h \
rd_listlogs.c rd_listlogs.h \
rd_listservices.c rd_listservices.h \
rd_listschedcodes.c rd_listschedcodes.h \
rd_listsystemsettings.c rd_listsystemsettings.h \
rd_removecart.c rd_removecart.h \
rd_removecut.c rd_removecut.h \
rd_savelog.c rd_savelog.h \
rd_trimaudio.c rd_trimaudio.h \
rd_unassignschedcode.c rd_unassignschedcode.h
librivwebcapi_la_LDFLAGS = -version-info $(INTERFACE_RIVWEBCAPI_CURRENT):$(INTERFACE_RIVWEBCAPI_REVISION):$(INTERFACE_RIVWEBCAPI_AGE)
includedir = $(prefix)/include/rivwebcapi
include_HEADERS = rd_addcart.h\
rd_addcut.h\
rd_addlog.h\
rd_assignschedcode.h\
rd_audioinfo.h\
rd_audiostore.h\
rd_cart.h\
rd_common.h\
rd_copyaudio.h\
rd_createticket.h\
rd_cut.h\
rd_deleteaudio.h\
rd_deletelog.h\
rd_editcart.h\
rd_editcut.h\
rd_export.h\
rd_exportpeaks.h\
rd_getuseragent.h\
rd_getversion.h\
rd_group.h\
rd_import.h\
rd_listcart.h\
rd_listcartschedcodes.h\
rd_listcarts.h\
rd_listcut.h\
rd_listcuts.h\
rd_listgroup.h\
rd_listgroups.h\
rd_listlog.h\
rd_listlogs.h\
rd_listschedcodes.h\
rd_listservices.h\
rd_listsystemsettings.h \
rd_savelog.h\
rd_schedcodes.h\
rd_removecart.h\
rd_removecut.h\
rd_trimaudio.h\
rd_unassignschedcode.h
CLEANFILES = *~\
moc_*\
*.lib\
*.obj\
*.qm
DISTCLEANFILES = rdpaths.h
MAINTAINERCLEANFILES = *~\
*.tar.gz\
aclocal.m4\
configure\
Makefile.in\
moc_*

View File

@@ -0,0 +1,264 @@
/* rd_addcart.c
*
* Implementation of the Add Cart Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_addcart.h"
#include "rd_common.h"
#include "rd_getuseragent.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
struct rd_cart *cart;
};
static void XMLCALL __AddCartElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"cart")==0) { // Allocate a new cart entry
xml_data->cart=realloc(xml_data->cart,
sizeof(struct rd_cart));
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __AddCartElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __AddCartElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_cart *cart=xml_data->cart;
char hold_datetime[25];
if(strcasecmp(el,"number")==0) {
sscanf(xml_data->strbuf,"%u",&cart->cart_number);
}
if(strcasecmp(el,"type")==0) {
if(strcasecmp(xml_data->strbuf,"audio")==0) {
cart->cart_type=TYPE_AUDIO;
}
else {
if(strcasecmp(xml_data->strbuf,"macro")==0) {
cart->cart_type=TYPE_MACRO;
}
else
{
/* This is ALL type */
cart->cart_type=TYPE_ALL;
}
}
}
if(strcasecmp(el,"groupName")==0) {
strlcpy(cart->cart_grp_name,xml_data->strbuf,11);
}
if(strcasecmp(el,"title")==0) {
strlcpy(cart->cart_title,xml_data->strbuf,256);
}
if(strcasecmp(el,"artist")==0) {
strlcpy(cart->cart_artist,xml_data->strbuf,256);
}
if(strcasecmp(el,"album")==0) {
strlcpy(cart->cart_album,xml_data->strbuf,256);
}
if(strcasecmp(el,"year")==0) {
sscanf(xml_data->strbuf,"%d",&cart->cart_year);
}
if(strcasecmp(el,"label")==0) {
strlcpy(cart->cart_label,xml_data->strbuf,65);
}
if(strcasecmp(el,"client")==0) {
strlcpy(cart->cart_client,xml_data->strbuf,65);
}
if(strcasecmp(el,"agency")==0) {
strlcpy(cart->cart_agency,xml_data->strbuf,65);
}
if(strcasecmp(el,"publisher")==0) {
strlcpy(cart->cart_publisher,xml_data->strbuf,65);
}
if(strcasecmp(el,"composer")==0) {
strlcpy(cart->cart_composer,xml_data->strbuf,65);
}
if(strcasecmp(el,"userDefined")==0) {
strlcpy(cart->cart_user_defined,xml_data->strbuf,256);
}
if(strcasecmp(el,"usageCode")==0) {
sscanf(xml_data->strbuf,"%d",&cart->cart_usage_code);
}
if(strcasecmp(el,"forcedLength")==0) {
sscanf(xml_data->strbuf,"%d",&cart->cart_forced_length);
}
if(strcasecmp(el,"averageLength")==0) {
sscanf(xml_data->strbuf,"%d",&cart->cart_average_length);
}
if(strcasecmp(el,"lengthDeviation")==0) {
sscanf(xml_data->strbuf,"%d",&cart->cart_length_deviation);
}
if(strcasecmp(el,"averageSegueLength")==0) {
sscanf(xml_data->strbuf,"%d",&cart->cart_average_segue_length);
}
if(strcasecmp(el,"averageHookLength")==0) {
sscanf(xml_data->strbuf,"%d",&cart->cart_average_hook_length);
}
if(strcasecmp(el,"cutQuantity")==0) {
sscanf(xml_data->strbuf,"%u",&cart->cart_cut_quantity);
}
if(strcasecmp(el,"lastCutPlayed")==0) {
sscanf(xml_data->strbuf,"%u",&cart->cart_last_cut_played);
}
if(strcasecmp(el,"validity")==0) {
sscanf(xml_data->strbuf,"%u",&cart->cart_validity);
}
if(strcasecmp(el,"enforceLength")==0) {
cart->cart_enforce_length=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"asyncronous")==0) {
cart->cart_asyncronous=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"owner")==0) {
strlcpy(cart->cart_owner,xml_data->strbuf,66);
}
if(strcasecmp(el,"metadataDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
cart->cart_metadata_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
}
size_t __AddCartCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_AddCart(struct rd_cart *cart[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char group[],
const char type[],
const unsigned cartnumber,
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/* Set number of recs so if fail already set */
*numrecs = 0;
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__AddCartElementStart,
__AddCartElementEnd);
XML_SetCharacterDataHandler(parser,__AddCartElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=12&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&GROUP_NAME=%s&TYPE=%s&CART_NUMBER=%u",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
curl_easy_escape(curl,group,0),
type,
cartnumber);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string,RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__AddCartCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
size_t len = strlen(errbuf);
#ifdef RIVC_DEBUG_OUT
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) { //Success
*cart=xml_data.cart;
*numrecs = 1;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr,"rd_addcart Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,42 @@
/* rd_addcart.h
*
* Header for the AddCart Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_ADDCART_H
#define RD_ADDCART_H
#include <rivwebcapi/rd_cart.h>
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
int RD_AddCart(struct rd_cart *cart[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char group[],
const char type[],
const unsigned cartnumber,
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_ADDCART_H

View File

@@ -0,0 +1,302 @@
/* rd_addcut.c
*
* Implementation of the Add Cut Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_addcut.h"
#include "rd_common.h"
#include "rd_getuseragent.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
struct rd_cut *cut;
};
static void XMLCALL __AddCutElementStart(void *data, const char *el,
const char **attr)
{
unsigned i;
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"cut")==0) { // Allocate a new cut entry
xml_data->cut=realloc(xml_data->cut,
sizeof(struct rd_cut));
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __AddCutElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __AddCutElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_cut *cut=xml_data->cut;
char hold_datetime[25];
if(strcasecmp(el,"cutName")==0) {
strlcpy(cut->cut_name,xml_data->strbuf,11);
}
if(strcasecmp(el,"cartNumber")==0) {
sscanf(xml_data->strbuf,"%u",&cut->cut_cart_number);
}
if(strcasecmp(el,"cutNumber")==0){
sscanf(xml_data->strbuf,"%u",&cut->cut_cut_number);
}
if(strcasecmp(el,"evergreen")==0) {
cut->cut_evergreen=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"description")==0) {
strlcpy(cut->cut_description,xml_data->strbuf,65);
}
if(strcasecmp(el,"outcue")==0) {
strlcpy(cut->cut_outcue,xml_data->strbuf,65);
}
if(strcasecmp(el,"isrc")==0) {
strlcpy(cut->cut_isrc,xml_data->strbuf,13);
}
if(strcasecmp(el,"isci")==0) {
strlcpy(cut->cut_isci,xml_data->strbuf,33);
}
if(strcasecmp(el,"length")==0){
sscanf(xml_data->strbuf,"%u",&cut->cut_length);
}
if(strcasecmp(el,"originDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
cut->cut_origin_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"startDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
cut->cut_start_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"endDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
cut->cut_end_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"sun")==0) {
cut->cut_sun=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"mon")==0) {
cut->cut_mon=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"tue")==0) {
cut->cut_tue=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"wed")==0) {
cut->cut_wed=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"thu")==0) {
cut->cut_thu=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"fri")==0) {
cut->cut_fri=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"sat")==0) {
cut->cut_sat=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"startDaypart")==0) {
strlcpy(cut->cut_start_daypart,xml_data->strbuf,15);
}
if(strcasecmp(el,"endDaypart")==0) {
strlcpy(cut->cut_end_daypart,xml_data->strbuf,15);
}
if(strcasecmp(el,"originName")==0) {
strlcpy(cut->cut_origin_name,xml_data->strbuf,65);
}
if(strcasecmp(el,"weight")==0) {
sscanf(xml_data->strbuf,"%u",&cut->cut_weight);
}
if(strcasecmp(el,"lastPlayDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
cut->cut_last_play_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"playCounter")==0) {
sscanf(xml_data->strbuf,"%u",&cut->cut_play_counter);
}
if(strcasecmp(el,"localCounter")==0) {
sscanf(xml_data->strbuf,"%u",&cut->cut_local_counter);
}
if(strcasecmp(el,"validity")==0) {
sscanf(xml_data->strbuf,"%u",&cut->cut_validity);
}
if(strcasecmp(el,"codingFormat")==0) {
sscanf(xml_data->strbuf,"%u",&cut->cut_coding_format);
}
if(strcasecmp(el,"sampleRate")==0) {
sscanf(xml_data->strbuf,"%u",&cut->cut_sample_rate);
}
if(strcasecmp(el,"bitRate")==0) {
sscanf(xml_data->strbuf,"%u",&cut->cut_bit_rate);
}
if(strcasecmp(el,"channels")==0) {
sscanf(xml_data->strbuf,"%u",&cut->cut_channels);
}
if(strcasecmp(el,"playGain")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_play_gain);
}
if(strcasecmp(el,"startPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_start_point);
}
if(strcasecmp(el,"endPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_end_point);
}
if(strcasecmp(el,"fadeupPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_fadeup_point);
}
if(strcasecmp(el,"fadedownPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_fadedown_point);
}
if(strcasecmp(el,"segueStartPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_segue_start_point);
}
if(strcasecmp(el,"segueEndPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_segue_end_point);
}
if(strcasecmp(el,"segueGain")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_segue_gain);
}
if(strcasecmp(el,"hookStartPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_hook_start_point);
}
if(strcasecmp(el,"hookEndPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_hook_end_point);
}
if(strcasecmp(el,"talkStartPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_talk_start_point);
}
if(strcasecmp(el,"talkEndPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_talk_end_point);
}
}
size_t __AddCutCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_AddCut(struct rd_cut *cut[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnumber,
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/* Set number of recs so if fail already set */
*numrecs = 0;
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__AddCutElementStart,
__AddCutElementEnd);
XML_SetCharacterDataHandler(parser,__AddCutElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=10&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&CART_NUMBER=%u",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
cartnumber);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__AddCutCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
size_t len = strlen(errbuf);
#ifdef RIVC_DEBUG_OUT
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
*cut=xml_data.cut;
*numrecs = 1;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr,"rd_addcut Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,41 @@
/* rd_addcart.h
*
* Header for the AddtCart Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_ADDCUT_H
#define RD_ADDCUT_H
#include <rivwebcapi/rd_cut.h>
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
int RD_AddCut(struct rd_cut *cut[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnumber,
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_ADDCUT_H

View File

@@ -0,0 +1,97 @@
/* rd_addlog.c
*
* Implementation of the AddLog Rivendell Access Library
*
* (C) Copyright 2017 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <curl/curl.h>
#include "rd_addlog.h"
#include "rd_getuseragent.h"
int RD_AddLog(const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char logname[],
const char servicename[],
const char user_agent[])
{
char post[1500];
char url[1500];
CURL *curl=NULL;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=29&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&LOG_NAME=%s&SERVICE_NAME=%s",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
curl_easy_escape(curl,logname,0),
curl_easy_escape(curl,servicename,0));
if (strlen(user_agent)> 0)
{
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
size_t len = strlen(errbuf);
#ifdef RIVC_DEBUG_OUT
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) { //Success
return 0;
}
return (int)response_code;
}

View File

@@ -0,0 +1,39 @@
/* rd_addlog.h
*
* Header for the AddLog Rivendell Access Library
*
* (C) Copyright 2017 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_ADDLOG_H
#define RD_ADDLOG_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
int RD_AddLog(const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char logname[],
const char servicename[],
const char user_agent[]);
_MYRIVLIB_FINI_DECL
#endif // RD_ADDLOG_H

View File

@@ -0,0 +1,177 @@
/* rd_assignschedulcodes.c
*
* Implementation of the AssignSchedulCodes Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_common.h"
#include "rd_getuseragent.h"
#include "rd_assignschedcode.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
};
static void XMLCALL __AssignSchedCodeElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __AssignSchedCodeElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __AssignSchedCodeElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
}
size_t __AssignSchedCodeCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_AssignSchedCode( const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnum,
const char code[],
const char user_agent[])
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
int i;
int code_valid = 1;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* Check Code */
for (i = 0 ; i < strlen(code) ; i++) {
if ((code[i]==32) || (i > 9)) {
code_valid=0;
break;
}
}
if (!code_valid)
{
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," Scheduler Code : %s Is Invalid! \n",code);
#endif
return -1;
}
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__AssignSchedCodeElementStart,
__AssignSchedCodeElementEnd);
XML_SetCharacterDataHandler(parser,__AssignSchedCodeElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=25&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&CART_NUMBER=%u&CODE=%s",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
cartnum,
curl_easy_escape(curl,code,0));
//
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__AssignSchedCodeCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
size_t len = strlen(errbuf);
#ifdef RIVC_DEBUG_OUT
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr,"rd_assignschedcode Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,39 @@
/* rd_assignschedcodes.h
*
* Header for the AssignSchedCodes Web Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_ASSIGNSCHEDCODE_H
#define RD_ASSIGNSCHEDCODE_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
int RD_AssignSchedCode(const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnum,
const char code[],
const char user_agent[]);
_MYRIVLIB_FINI_DECL
#endif // RD_ASSIGNSCHEDCODE_H

View File

@@ -0,0 +1,195 @@
/* rd_audioinfo.c
*
* Implementation of the AudioInfo Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_common.h"
#include "rd_audioinfo.h"
#include "rd_getuseragent.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
struct rd_audioinfo *audioinfo;
};
static void XMLCALL __AudioInfoElementStart(void *data, const char *el,
const char **attr)
{
unsigned i;
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"audioInfo")==0) { // Allocate a new audioinfo entry
xml_data->audioinfo=realloc(xml_data->audioinfo,
sizeof(struct rd_audioinfo));
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __AudioInfoElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __AudioInfoElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_audioinfo *audioinfo=xml_data->audioinfo;
if(strcasecmp(el,"cartNumber")==0) {
sscanf(xml_data->strbuf,"%u",&audioinfo->cart_number);
}
if(strcasecmp(el,"cutNumber")==0){
sscanf(xml_data->strbuf,"%u",&audioinfo->cut_number);
}
if(strcasecmp(el,"format")==0) {
sscanf(xml_data->strbuf,"%d",&audioinfo->format);
}
if(strcasecmp(el,"channels")==0) {
sscanf(xml_data->strbuf,"%d",&audioinfo->channels);
}
if(strcasecmp(el,"sampleRate")==0) {
sscanf(xml_data->strbuf,"%d",&audioinfo->samplerate);
}
if(strcasecmp(el,"frames")==0){
sscanf(xml_data->strbuf,"%u",&audioinfo->frames);
}
if(strcasecmp(el,"length")==0){
sscanf(xml_data->strbuf,"%u",&audioinfo->length);
}
}
size_t __AudioInfoCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_AudioInfo(struct rd_audioinfo *audioinfo[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnumber,
const unsigned cutnumber,
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* Set number of recs so if fail already set */
*numrecs = 0;
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__AudioInfoElementStart,
__AudioInfoElementEnd);
XML_SetCharacterDataHandler(parser,__AudioInfoElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=19&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&CART_NUMBER=%u&CUT_NUMBER=%u",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
cartnumber,
cutnumber);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__AudioInfoCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
size_t len = strlen(errbuf);
#ifdef RIVC_DEBUG_OUT
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
*audioinfo=xml_data.audioinfo;
*numrecs = 1;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_audioinfo Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,50 @@
/* rd_audioinfo.h
*
* Header for the ListCuts Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_AUDIOINFO_H
#define RD_AUDIOINFO_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
struct rd_audioinfo {
unsigned cart_number;
unsigned cut_number;
int format;
int channels;
int samplerate;
unsigned frames;
unsigned length;
};
int RD_AudioInfo(struct rd_audioinfo *audioinfo[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnumber,
const unsigned cutnumber,
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_AUDIOINFO_H

View File

@@ -0,0 +1,175 @@
/* rd_audiostore.c
*
* Implementation of the AudioStore Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_common.h"
#include "rd_audiostore.h"
#include "rd_getuseragent.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
struct rd_audiostore *audiostore;
};
static void XMLCALL __AudioStoreElementStart(void *data, const char *el,
const char **attr)
{
unsigned i;
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"audioStore")==0) { // Allocate a new audiostore entry
xml_data->audiostore=realloc(xml_data->audiostore,
sizeof(struct rd_audiostore));
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __AudioStoreElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __AudioStoreElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_audiostore *audiostore=xml_data->audiostore;
if(strcasecmp(el,"freeBytes")==0) {
sscanf(xml_data->strbuf,"%lu",&audiostore->freebytes);
}
if(strcasecmp(el,"totalBytes")==0){
sscanf(xml_data->strbuf,"%lu",&audiostore->totalbytes);
}
}
size_t __AudioStoreCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_AudioStore(struct rd_audiostore *audiosto[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* Set number of recs so if fail already set */
*numrecs = 0;
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__AudioStoreElementStart,
__AudioStoreElementEnd);
XML_SetCharacterDataHandler(parser,__AudioStoreElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=23&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0));
//
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__AudioStoreCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
size_t len = strlen(errbuf);
#ifdef RIVC_DEBUG_OUT
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
*audiosto=xml_data.audiostore;
*numrecs = 1;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_audiostore Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,45 @@
/* rd_audiostore.h
*
* Header for the AudioStore Web Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_AUDIOSTORE_H
#define RD_AUDIOSTORE_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
struct rd_audiostore {
long unsigned freebytes;
long unsigned totalbytes;
};
int RD_AudioStore(struct rd_audiostore *audiostore[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_AUDIOSTORE_H

View File

@@ -0,0 +1,53 @@
/* rd_cart.h
*
* Header for the RDCART Structure Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
*/
#ifndef RD_CART_H
#define RD_CART_H
#include <time.h>
enum CART_TYPE {TYPE_ALL,TYPE_AUDIO,TYPE_MACRO};
struct rd_cart {
unsigned cart_number;
unsigned cart_type;
char cart_grp_name[11];
char cart_title[256];
char cart_artist[256];
char cart_album[256];
int cart_year;
char cart_label[65];
char cart_client[65];
char cart_agency[65];
char cart_publisher[65];
char cart_composer[65];
char cart_conductor[65];
char cart_user_defined[256];
int cart_usage_code;
int cart_forced_length;
int cart_average_length;
int cart_length_deviation;
int cart_average_segue_length;
int cart_average_hook_length;
unsigned cart_cut_quantity;
unsigned cart_last_cut_played;
unsigned cart_validity;
int cart_enforce_length;
int cart_asyncronous;
char cart_owner[65];
char cart_notes[1024];
struct tm cart_metadata_datetime;
};
#endif //RD_CART_H

View File

@@ -0,0 +1,349 @@
/* rd_common.c
*
* Common Utility Functions for the Rivendell Access Library
*
* (C) Copyright 2015 Fred Gleason <fredg@paravelsystems.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include "rd_common.h"
unsigned RD_ReadBool(const char *val)
{
if((strcasecmp(val,"true")==0)||(strcasecmp(val,"yes")==0)||
(strcasecmp(val,"on")==0)) {
return 1;
}
else {
return 0;
}
}
/*******************************************************************
* RD_Cnv_DTString_to_tm
* Take a DateTime String and converts to a tm struct.
* Assumes a Z means Zulu (GMT) Always returns localtime
* in tm struct pointer. Returns null tm on invalid date length
*******************************************************************/
struct tm RD_Cnv_DTString_to_tm( const char *datein)
{
struct tm datetimetm = {0};
struct tm *tmptr;
time_t rawtime;
time_t newrawtime;
char theyear[5];
char themonth[3];
char theday[3];
char thehr[3];
char themin[3];
char thesec[3];
char plusminusz[2];
char offsethr[3];
char offsetmin[3];
double offsetfromutc = 0;
int offhr = 0;
int offmin = 0;
int val;
tmptr = &datetimetm;
if ((strlen(datein) < 19) || // INVALID DATE
(strlen(datein) > 26) )
return datetimetm;
strlcpy(theyear,datein,4);
strlcpy(themonth,datein+5,2);
strlcpy(theday,datein+8,2);
strlcpy(thehr,datein+11,2);
strlcpy(themin,datein+14,2);
strlcpy(thesec,datein+17,2);
if (strlen(datein) > 19)
{
strlcpy(plusminusz,datein+19,1);
if ( (( strcmp(plusminusz,"+"))==0) ||
(( strcmp(plusminusz,"-"))==0) )
{
strlcpy(offsethr,datein+20,2);
strlcpy(offsetmin,datein+23,2);
}
}
val = atoi(theyear) - 1900;
tmptr->tm_year = val;
val = atoi(themonth) - 1;
tmptr->tm_mon = val;
tmptr->tm_mday = atoi(theday);
tmptr->tm_hour = atoi(thehr);
tmptr->tm_min = atoi(themin);
tmptr->tm_sec = atoi(thesec);
/* This is to fix if Windows Assumes apply DST */
#ifdef _WIN32
tmptr->tm_isdst = -1;
#endif
rawtime = mktime (tmptr);
newrawtime = rawtime;
if ((strcmp(plusminusz,"Z")) != 0)
{
if (strlen(datein)==25)
{
offhr = atoi(offsethr);
offmin = atoi(offsetmin);
}
if ((strcmp(plusminusz,"-"))== 0)
{
newrawtime = rawtime + ((offhr * 3600) +
(offmin * 60));
}
else
{
newrawtime = rawtime - ((offhr * 3600) -
(offmin * 60));
}
}
// Get the local offset from UTC
offsetfromutc = get_local_offset();
newrawtime += offsetfromutc;
#ifdef _WIN32
tmptr = localtime(&newrawtime);
#else
localtime_r(&newrawtime,tmptr);
#endif
return datetimetm;
}
/****************************************************************
* strlcpy
* Copies a strng buffer into a string buffer with size bufsiz
* Returns size_t length copied. Null Terminates Automatically
*****************************************************************/
size_t strlcpy(char * dest, const char* src, size_t bufsize)
{
size_t srclen = strlen(src);
size_t len;
if (bufsize == 0)
return bufsize;
len = (bufsize < srclen) ? bufsize : srclen;
memcpy(dest,src,len);
dest[len]='\0';
return len;
}
/****************************************************************
* RD_Cnv_tm_to_DTString
* Copies tm struct values into a date string. Returns
* size_t length copied. Returns 0 if invalid tm struct.
* Automatically URL Encodes colon and the plus sign.
*****************************************************************/
size_t RD_Cnv_tm_to_DTString(struct tm *tmptr,char * dest)
{
char theyear[5];
char themonth[3];
char theday[3];
char thehr[3];
char themin[3];
char thesec[3];
char plusminus[3];
char minus[2] = "-";
char colon_sep[4] = "%3a";
char T_sep[2] = "T";
char offsethr[3];
char offsetmin[3];
double offsetfromutc;
int offhr = 0;
int offmin = 0;
int val;
int leap = 0;
if (!validate_tm(tmptr))
{
dest[0]=0;
return 0;
}
offsetfromutc = get_local_offset();
if (offsetfromutc > 0)
strlcpy(plusminus,"%2b",3);
else
strlcpy(plusminus,"-",1);
offhr = (int) (offsetfromutc / 3600);
double hold_min;
double divby = 3600;
hold_min = fmod(offsetfromutc,divby);
offmin = (int) (hold_min / 60);
sprintf(offsethr,"%02d",abs(offhr));
sprintf(offsetmin,"%02d",abs(offmin));
val = tmptr->tm_year + 1900;
sprintf(theyear,"%d",val);
val = tmptr->tm_mon + 1;
sprintf(themonth,"%02d",val);
sprintf(theday,"%02d",tmptr->tm_mday);
sprintf(thehr,"%02d",tmptr->tm_hour);
sprintf(themin,"%02d",tmptr->tm_min);
sprintf(thesec,"%02d",tmptr->tm_sec);
strlcpy(dest,theyear,4);
strcat(dest, minus);
strcat(dest,themonth);
strcat(dest, minus);
strcat(dest,theday);
strcat(dest,T_sep);
strcat(dest,thehr);
strcat(dest,colon_sep);
strcat(dest,themin);
strcat(dest,colon_sep);
strcat(dest,thesec);
strcat(dest,plusminus);
strcat(dest,offsethr);
strcat(dest,colon_sep);
strcat(dest,offsetmin);
return strlen(dest);
}
/****************************************************************
* validate tm
* Validates a tm struct YYYY-MM-DD hh:mm:ss
* Returns 1 if successful 0 if error
****************************************************************/
int validate_tm (struct tm *tmptr)
{
int monthdays[12]={31,28,31,30,31,30,31,31,30,31,30,31};
int val;
int leap = 0;
val = tmptr->tm_year + 1900;
if ((val < 1900) || (val > 9999) )
return 0;
if ( (tmptr->tm_mon < 0) ||
(tmptr->tm_mon > 11))
return 0;
if ((tmptr->tm_mday == 29 ) && (tmptr->tm_mon == 1))
{
if ( (val % 400) == 0 )
leap = 1;
else if ((val %100) == 0)
leap = 0;
else if ((val % 4) == 0)
leap = 1;
else
leap = 0;
if (!leap)
return 0;
}
if ( (tmptr->tm_mday > monthdays[tmptr->tm_mon]) ||
(tmptr->tm_mday <=0) )
return 0;
if ( (tmptr->tm_sec > 61) ||
(tmptr->tm_sec < 0))
return 0;
if ( (tmptr->tm_min > 59) ||
(tmptr->tm_min < 0))
return 0;
if ( (tmptr->tm_hour > 23) ||
(tmptr->tm_hour < 0))
return 0;
return 1;
}
/****************************************************************
* get_local_offset
* returns local UTC Offset
* Returns 1 if successful 0 if error
****************************************************************/
double get_local_offset()
{
time_t currtime;
struct tm * timeinfo;
time( &currtime );
timeinfo = gmtime (&currtime);
time_t utc = mktime (timeinfo);
timeinfo = localtime(&currtime);
time_t local = mktime(timeinfo);
double offsetfromutc = difftime(local,utc);
#ifdef _WIN32
if (timeinfo->tm_isdst)
offsetfromutc += 3600;
#endif
return offsetfromutc;
}
/****************************************************************
* RD_Cnv_TString_to_msec
* Converts a relative-to-midnight start time string ("HH:MM:SS.ZZZ")
* and returns it as milliseconds after midnight, or -1 if
* the conversion fails.
*****************************************************************/
int RD_Cnv_TString_to_msec(const char *str)
{
int hour;
int minute;
int second;
int tenth;
if(strlen(str)<10) {
return -1;
}
if(sscanf(str,"%02d",&hour)!=1) {
return -1;
}
if((hour<0)||(hour>23)) {
return -1;
}
if(sscanf(str+3,"%02d",&minute)!=1) {
return -1;
}
if((minute<0)||(minute>59)) {
return -1;
}
if(sscanf(str+6,"%02d",&second)!=1) {
return -1;
}
if((second<0)||(second>59)) {
return -1;
}
if(sscanf(str+9,"%1d",&tenth)!=1) {
return -1;
}
if((tenth<0)||(tenth>9)) {
return -1;
}
return 3600000*hour+60000*minute+1000*second+100*tenth;
}
/****************************************************************
* RD_Cnv_msec_to_TString
* Converts a milliseconds after midnight integer to
* time string ("HH:MM:SS.ZZZ"), returning the length
* of the string.
*****************************************************************/
size_t RD_Cnv_msec_to_TString(char *str, size_t len,int msec)
{
int hour;
int minute;
int second;
int tenth;
if(msec<0) {
str[len]=0;
return 0;
}
hour=msec/3600000;
minute=(msec-3600000*hour)/60000;
second=(msec-3600000*hour-60000*minute)/1000;
tenth=(msec-3600000*hour-60000*minute-1000*second)/100;
snprintf(str,len,"%02d:%02d:%02d.%1d",hour,minute,second,tenth);
return strlen(str);
}

View File

@@ -0,0 +1,67 @@
/* rd_common.h
*
* Common Utility Functions for the Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <time.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <math.h>
#ifndef RD_COMMON_H
#define RD_COMMON_H
#if ((defined(_WINDLL)) || (defined(_WIN32)))
#ifndef MINGW32
#define strcpy_s strcpy
#define strncpy_s strncpy
#define strcat_s strcat
#define snprintf _snprintf
#define strcasecmp _stricmp
#define sscanf_s sscanf
#endif // MINGW32
#define VERSION "0.0.6"
#endif
/* #define RIVC_DEBUG_OUT Uncomment for stderr output */
#if defined(__cplusplus)
#define _MYRIVLIB_INIT_DECL extern "C" {
#define _MYRIVLIB_FINI_DECL }
#else
#define _MYRIVLIB_INIT_DECL
#define _MYRIVLIB_FINI_DECL
#endif
extern unsigned RD_ReadBool(const char *val);
extern struct tm RD_Cnv_DTString_to_tm( const char *datein);
extern size_t RD_Cnv_tm_to_DTString(struct tm *tmptr,char * dest);
extern size_t strlcpy(char * dest, const char* src, size_t bufsize);
extern double get_local_offset();
extern int validate_tm (struct tm *tmptr);
extern int RD_Cnv_TString_to_msec(const char *str);
extern size_t RD_Cnv_msec_to_TString(char *str, size_t len,int msec);
#endif // RD_COMMON_H

View File

@@ -0,0 +1,159 @@
/* rd_copyaudio.c
*
* Implementation of the Copy Audio Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_common.h"
#include "rd_copyaudio.h"
#include "rd_getuseragent.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
};
static void XMLCALL __CopyAudioElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __CopyAudioElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __CopyAudioElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
}
size_t __CopyAudioCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_CopyAudio( const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned src_cartnumber,
const unsigned src_cutnumber,
const unsigned dest_cartnumber,
const unsigned dest_cutnumber,
const char user_agent[])
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__CopyAudioElementStart,
__CopyAudioElementEnd);
XML_SetCharacterDataHandler(parser,__CopyAudioElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=18&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&SOURCE_CART_NUMBER=%u&SOURCE_CUT_NUMBER=%u&DESTINATION_CART_NUMBER=%u&DESTINATION_CUT_NUMBER=%u",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
src_cartnumber,
src_cutnumber,
dest_cartnumber,
dest_cutnumber);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string , RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__CopyAudioCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
size_t len = strlen(errbuf);
#ifdef RIVC_DEBUG_OUT
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) { //Success
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr,"rd_copyaudio Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,42 @@
/* rd_copyaudio.h
*
* Header for the Copy Audio Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_COPYAUDIO_H
#define RD_COPYAUDIO_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
int RD_CopyAudio(const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned src_cartnumber,
const unsigned src_cutnumber,
const unsigned dest_cartnumber,
const unsigned dest_cutnumber,
const char user_agent[]);
_MYRIVLIB_FINI_DECL
#endif // RD_COPYAUDIO_H

View File

@@ -0,0 +1,175 @@
/* rd_createticket.c
*
* Implementation of the Create Ticket Rivendell Access Library
*
* (C) Copyright 2017 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_common.h"
#include "rd_getuseragent.h"
#include "rd_createticket.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
struct rd_ticketinfo *ticketinfo;
};
static void XMLCALL __CreateTicketElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"ticketInfo")==0) { // Allocate a new ticketinfo entry
xml_data->ticketinfo=realloc(xml_data->ticketinfo,
sizeof(struct rd_ticketinfo));
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __CreateTicketElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __CreateTicketElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_ticketinfo *ticketinfo=xml_data->ticketinfo;
char hold_datetime[25];
if(strcasecmp(el,"ticket")==0) {
strlcpy(ticketinfo->ticket,xml_data->strbuf,41);
}
if(strcasecmp(el,"expires")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
ticketinfo->tkt_expiration_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
}
size_t __CreateTicketCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_CreateTicket(struct rd_ticketinfo *ticketinfo[],
const char hostname[],
const char username[],
const char passwd[],
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* Set number of recs so if fail already set */
*numrecs = 0;
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__CreateTicketElementStart,
__CreateTicketElementEnd);
XML_SetCharacterDataHandler(parser,__CreateTicketElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=31&LOGIN_NAME=%s&PASSWORD=%s",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0));
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string , RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__CreateTicketCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
*ticketinfo=xml_data.ticketinfo;
*numrecs = 1;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr,"rd_createticket Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,43 @@
/* rd_createticket.h
*
* Header for the Create Ticket Rivendell Access Library
*
* (C) Copyright 2017 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_CREATETICKET_H
#define RD_CREATETICKET_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
struct rd_ticketinfo {
char ticket[41];
struct tm tkt_expiration_datetime;
};
int RD_CreateTicket(struct rd_ticketinfo *ticketinfo[],
const char hostname[],
const char username[],
const char passwd[],
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_CREATETICKET_H

View File

@@ -0,0 +1,75 @@
/* rd_cut.h
*
* Header for the RDCUT Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_CUT_H
#define RD_CUT_H
#include <time.h>
struct rd_cut {
char cut_name[11];
unsigned cut_cart_number;
unsigned cut_cut_number;
int cut_evergreen;
char cut_description[65];
char cut_outcue[65];
char cut_isrc[13];
char cut_isci[33];
unsigned cut_length;
struct tm cut_origin_datetime;
struct tm cut_start_datetime;
struct tm cut_end_datetime;
int cut_sun;
int cut_mon;
int cut_tue;
int cut_wed;
int cut_thu;
int cut_fri;
int cut_sat;
char cut_start_daypart[15];
char cut_end_daypart[15];
char cut_origin_name[65];
char cut_origin_login_name[256];
char cut_source_hostname[256];
unsigned cut_weight;
struct tm cut_last_play_datetime;
unsigned cut_play_counter;
unsigned cut_local_counter;
unsigned cut_validity;
unsigned cut_coding_format;
unsigned cut_sample_rate;
unsigned cut_bit_rate;
unsigned cut_channels;
int cut_play_gain;
int cut_start_point;
int cut_end_point;
int cut_fadeup_point;
int cut_fadedown_point;
int cut_segue_start_point;
int cut_segue_end_point;
int cut_segue_gain;
int cut_hook_start_point;
int cut_hook_end_point;
int cut_talk_start_point;
int cut_talk_end_point;
};
#endif // RD_CUT_H

View File

@@ -0,0 +1,156 @@
/* rd_deleteaudio.c
*
* Implementation of the Delete Audio Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_common.h"
#include "rd_deleteaudio.h"
#include "rd_getuseragent.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
};
static void XMLCALL __DeleteAudioElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __DeleteAudioElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __DeleteAudioElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
}
size_t __DeleteAudioCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_DeleteAudio( const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnumber,
const unsigned cutnumber,
const char user_agent[])
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__DeleteAudioElementStart,
__DeleteAudioElementEnd);
XML_SetCharacterDataHandler(parser,__DeleteAudioElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=3&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&CART_NUMBER=%u&CUT_NUMBER=%u",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
cartnumber,
cutnumber);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__DeleteAudioCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) { //Success
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr,"rd_deleteaudio Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,39 @@
/* rd_deleteaudio.h
*
* Header for the Delete Audio Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_DELETEAUDIO_H
#define RD_DELETEAUDIO_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
int RD_DeleteAudio(const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnumber,
const unsigned cutnumber,
const char user_agent[]);
_MYRIVLIB_FINI_DECL
#endif // RDDELETEAUDIO_H

View File

@@ -0,0 +1,96 @@
/* rd_deletecart.c
*
* Header for the DeleteLog Rivendell Access Library
*
* (C) Copyright 2017 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <curl/curl.h>
#include "rd_getuseragent.h"
#include "rd_deletelog.h"
int RD_DeleteLog(const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char logname[],
const char user_agent[])
{
char post[1500];
char url[1500];
CURL *curl=NULL;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=30&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&LOG_NAME=%s",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
curl_easy_escape(curl,logname,0));
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) { //Success
return 0;
}
return (int)response_code;
}

View File

@@ -0,0 +1,38 @@
/* rd_deletecart.h
*
* Header for the DeleteLog Rivendell Access Library
*
* (C) Copyright 2017 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_DELETELOG_H
#define RD_DELETELOG_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
int RD_DeleteLog(const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char logname[],
const char user_agent[]);
_MYRIVLIB_FINI_DECL
#endif // RD_DELETELOG_H

View File

@@ -0,0 +1,366 @@
/* rd_editcart.c
*
* Implementation of the Edit Cart Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_common.h"
#include "rd_getuseragent.h"
#include "rd_editcart.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
struct rd_cart *cart;
};
static void XMLCALL __EditCartElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"cart")==0) { // Allocate a new cart entry
xml_data->cart=realloc(xml_data->cart,
sizeof(struct rd_cart));
memset(xml_data->cart,0,sizeof(struct rd_cart));
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __EditCartElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __EditCartElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_cart *cart=xml_data->cart;
char hold_datetime[25];
if(strcasecmp(el,"number")==0) {
sscanf(xml_data->strbuf,"%u",&cart->cart_number);
}
if(strcasecmp(el,"type")==0) {
if(strcasecmp(xml_data->strbuf,"audio")==0) {
cart->cart_type=TYPE_AUDIO;
}
else {
if(strcasecmp(xml_data->strbuf,"macro")==0) {
cart->cart_type=TYPE_MACRO;
}
else
{
/* This is ALL type */
cart->cart_type=TYPE_ALL;
}
}
}
if(strcasecmp(el,"groupName")==0) {
strlcpy(cart->cart_grp_name,xml_data->strbuf,10);
}
if(strcasecmp(el,"title")==0) {
strlcpy(cart->cart_title,xml_data->strbuf,255);
}
if(strcasecmp(el,"artist")==0) {
strlcpy(cart->cart_artist,xml_data->strbuf,255);
}
if(strcasecmp(el,"album")==0) {
strlcpy(cart->cart_album,xml_data->strbuf,255);
}
if(strcasecmp(el,"year")==0) {
sscanf(xml_data->strbuf,"%d",&cart->cart_year);
}
if(strcasecmp(el,"label")==0) {
strlcpy(cart->cart_label,xml_data->strbuf,64);
}
if(strcasecmp(el,"client")==0) {
strlcpy(cart->cart_client,xml_data->strbuf,64);
}
if(strcasecmp(el,"agency")==0) {
strlcpy(cart->cart_agency,xml_data->strbuf,64);
}
if(strcasecmp(el,"publisher")==0) {
strlcpy(cart->cart_publisher,xml_data->strbuf,64);
}
if(strcasecmp(el,"composer")==0) {
strlcpy(cart->cart_composer,xml_data->strbuf,64);
}
if(strcasecmp(el,"conductor")==0) {
strlcpy(cart->cart_conductor,xml_data->strbuf,64);
}
if(strcasecmp(el,"userDefined")==0) {
strlcpy(cart->cart_user_defined,xml_data->strbuf,255);
}
if(strcasecmp(el,"usageCode")==0) {
sscanf(xml_data->strbuf,"%d",&cart->cart_usage_code);
}
if(strcasecmp(el,"forcedLength")==0) {
sscanf(xml_data->strbuf,"%d",&cart->cart_forced_length);
}
if(strcasecmp(el,"averageLength")==0) {
sscanf(xml_data->strbuf,"%d",&cart->cart_average_length);
}
if(strcasecmp(el,"lengthDeviation")==0) {
sscanf(xml_data->strbuf,"%d",&cart->cart_length_deviation);
}
if(strcasecmp(el,"averageSegueLength")==0) {
sscanf(xml_data->strbuf,"%d",&cart->cart_average_segue_length);
}
if(strcasecmp(el,"averageHookLength")==0) {
sscanf(xml_data->strbuf,"%d",&cart->cart_average_hook_length);
}
if(strcasecmp(el,"cutQuantity")==0) {
sscanf(xml_data->strbuf,"%u",&cart->cart_cut_quantity);
}
if(strcasecmp(el,"lastCutPlayed")==0) {
sscanf(xml_data->strbuf,"%u",&cart->cart_last_cut_played);
}
if(strcasecmp(el,"validity")==0) {
sscanf(xml_data->strbuf,"%u",&cart->cart_validity);
}
if(strcasecmp(el,"enforceLength")==0) {
cart->cart_enforce_length=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"asyncronous")==0) {
cart->cart_asyncronous=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"owner")==0) {
strlcpy(cart->cart_owner,xml_data->strbuf,64);
}
if(strcasecmp(el,"notes")==0 ){
/* handle multiple NOTE Lines */
strlcpy(cart->cart_notes,xml_data->strbuf,1024);
}
}
size_t __EditCartCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_EditCart(struct rd_cart *cart[],
struct edit_cart_values edit_c_values,
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnum,
const char user_agent[],
unsigned *numrecs)
{
char post[3350];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/* Set number of recs so if fail already set */
*numrecs = 0;
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__EditCartElementStart,
__EditCartElementEnd);
XML_SetCharacterDataHandler(parser,__EditCartElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,3350,"COMMAND=14&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&CART_NUMBER=%u",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
cartnum);
Build_Post_Cart_Fields(post,curl,edit_c_values);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__EditCartCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) { //Success
*cart=xml_data.cart;
*numrecs = 1;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_editcart Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}
void Build_Post_Cart_Fields(char *post, CURL *curl, struct edit_cart_values edit_values)
{
char buffer[1024];
/* Copy all of the applicable values into the post string */
if (edit_values.use_cart_grp_name)
{
snprintf(buffer,1024,"&GROUP_NAME=%s",curl_easy_escape(curl,edit_values.cart_grp_name,0));
strcat(post,buffer);
}
if (edit_values.use_cart_title)
{
snprintf(buffer,1024,"&TITLE=%s",curl_easy_escape(curl,edit_values.cart_title,0));
strcat(post,buffer);
}
if (edit_values.use_cart_artist)
{
snprintf(buffer,1024,"&ARTIST=%s",curl_easy_escape(curl,edit_values.cart_artist,0));
strcat(post,buffer);
}
if (edit_values.use_cart_album)
{
snprintf(buffer,1024,"&ALBUM=%s",curl_easy_escape(curl,edit_values.cart_album,0));
strcat(post,buffer);
}
if (edit_values.use_cart_year)
{
snprintf(buffer,1024,"&YEAR=%d",edit_values.cart_year);
strcat(post,buffer);
}
if (edit_values.use_cart_label)
{
snprintf(buffer,1024,"&LABEL=%s",curl_easy_escape(curl,edit_values.cart_label,0));
strcat(post,buffer);
}
if (edit_values.use_cart_client)
{
snprintf(buffer,1024,"&CLIENT=%s",curl_easy_escape(curl,edit_values.cart_client,0));
strcat(post,buffer);
}
if (edit_values.use_cart_agency)
{
snprintf(buffer,1024,"&AGENCY=%s",curl_easy_escape(curl,edit_values.cart_agency,0));
strcat(post,buffer);
}
if (edit_values.use_cart_publisher)
{
snprintf(buffer,1024,"&PUBLISHER=%s",curl_easy_escape(curl,edit_values.cart_publisher,0));
strcat(post,buffer);
}
if (edit_values.use_cart_composer)
{
snprintf(buffer,1024,"&COMPOSER=%s",curl_easy_escape(curl,edit_values.cart_composer,0));
strcat(post,buffer);
}
if (edit_values.use_cart_conductor)
{
snprintf(buffer,1024,"&CONDUCTOR=%s",curl_easy_escape(curl,edit_values.cart_conductor,0));
strcat(post,buffer);
}
if (edit_values.use_cart_user_defined)
{
snprintf(buffer,1024,"&USER_DEFINED=%s",curl_easy_escape(curl,edit_values.cart_user_defined,0));
strcat(post,buffer);
}
if (edit_values.use_cart_usage_code)
{
snprintf(buffer,1024,"&USAGE_CODE=%d",edit_values.cart_usage_code);
strcat(post,buffer);
}
if (edit_values.use_cart_forced_length)
{
snprintf(buffer,1024,"&FORCED_LENGTH=%d",edit_values.cart_forced_length);
strcat(post,buffer);
}
if (edit_values.use_cart_enforce_length)
{
snprintf(buffer,1024,"&ENFORCE_LENGTH=%d",edit_values.cart_enforce_length);
strcat(post,buffer);
}
if (edit_values.use_cart_asyncronous)
{
snprintf(buffer,1024,"&ASYNCRONOUS=%d",edit_values.cart_asyncronous);
strcat(post,buffer);
}
if (edit_values.use_cart_owner)
{
snprintf(buffer,1024,"&OWNER=%s",curl_easy_escape(curl,edit_values.cart_owner,0));
strcat(post,buffer);
}
if (edit_values.use_cart_notes)
{
snprintf(buffer,1024,"&NOTES=%s",curl_easy_escape(curl,edit_values.cart_notes,0));
strcat(post,buffer);
}
return;
}

View File

@@ -0,0 +1,86 @@
/* rd_editcart.h
*
* Header for the Edit Cart Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_EDITCART_H
#define RD_EDITCART_H
#include <curl/curl.h>
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
#include <rivwebcapi/rd_cart.h>
struct edit_cart_values {
char cart_grp_name[11];
int use_cart_grp_name;
char cart_title[256];
int use_cart_title;
char cart_artist[256];
int use_cart_artist;
char cart_album[256];
int use_cart_album;
int cart_year;
int use_cart_year;
char cart_label[65];
int use_cart_label;
char cart_client[65];
int use_cart_client;
char cart_agency[65];
int use_cart_agency;
char cart_publisher[65];
int use_cart_publisher;
char cart_composer[65];
int use_cart_composer;
char cart_conductor[65];
int use_cart_conductor;
char cart_user_defined[256];
int use_cart_user_defined;
int cart_usage_code;
int use_cart_usage_code;
int cart_forced_length;
int use_cart_forced_length;
int cart_enforce_length;
int use_cart_enforce_length;
int cart_asyncronous;
int use_cart_asyncronous;
char cart_owner[65];
int use_cart_owner;
char cart_notes[1024];
int use_cart_notes;
};
int RD_EditCart(struct rd_cart *cart[],
struct edit_cart_values edit_c_values,
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnum,
const char user_agent[],
unsigned *numrecs);
void Build_Post_Cart_Fields(char *post, CURL * curl, struct edit_cart_values edit_values);
_MYRIVLIB_FINI_DECL
#endif // RD_EDITCART_H

View File

@@ -0,0 +1,499 @@
/* rd_editcut.c
*
* Implementation of the Edit Cut Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_common.h"
#include "rd_getuseragent.h"
#include "rd_editcut.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
struct rd_cut *cut;
};
static void XMLCALL __EditCutElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"cut")==0) { // Allocate a new cut entry
xml_data->cut=realloc(xml_data->cut,
sizeof(struct rd_cut));
}
strncpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __EditCutElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __EditCutElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_cut *cut=xml_data->cut;
char hold_datetime[25];
if(strcasecmp(el,"cutName")==0) {
strncpy(cut->cut_name,xml_data->strbuf,11);
}
if(strcasecmp(el,"cartNumber")==0) {
sscanf(xml_data->strbuf,"%u",&cut->cut_cart_number);
}
if(strcasecmp(el,"cutNumber")==0){
sscanf(xml_data->strbuf,"%u",&cut->cut_cut_number);
}
if(strcasecmp(el,"evergreen")==0) {
cut->cut_evergreen=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"description")==0) {
strncpy(cut->cut_description,xml_data->strbuf,65);
}
if(strcasecmp(el,"outcue")==0) {
strncpy(cut->cut_outcue,xml_data->strbuf,65);
}
if(strcasecmp(el,"isrc")==0) {
strncpy(cut->cut_isrc,xml_data->strbuf,13);
}
if(strcasecmp(el,"isci")==0) {
strncpy(cut->cut_isci,xml_data->strbuf,33);
}
if(strcasecmp(el,"originDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
cut->cut_origin_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"startDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
cut->cut_start_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"endDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
cut->cut_end_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"sun")==0) {
cut->cut_sun=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"mon")==0) {
cut->cut_mon=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"tue")==0) {
cut->cut_tue=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"wed")==0) {
cut->cut_wed=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"thu")==0) {
cut->cut_thu=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"fri")==0) {
cut->cut_fri=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"sat")==0) {
cut->cut_sat=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"startDaypart")==0) {
strncpy(cut->cut_start_daypart,xml_data->strbuf,15);
}
if(strcasecmp(el,"endDaypart")==0) {
strncpy(cut->cut_end_daypart,xml_data->strbuf,15);
}
if(strcasecmp(el,"originName")==0) {
strncpy(cut->cut_origin_name,xml_data->strbuf,65);
}
if(strcasecmp(el,"weight")==0) {
sscanf(xml_data->strbuf,"%u",&cut->cut_weight);
}
if(strcasecmp(el,"startPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_start_point);
}
if(strcasecmp(el,"endPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_end_point);
}
if(strcasecmp(el,"fadeupPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_fadeup_point);
}
if(strcasecmp(el,"fadedownPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_fadedown_point);
}
if(strcasecmp(el,"segueStartPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_segue_start_point);
}
if(strcasecmp(el,"segueEndPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_segue_end_point);
}
if(strcasecmp(el,"segueGain")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_segue_gain);
}
if(strcasecmp(el,"hookStartPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_hook_start_point);
}
if(strcasecmp(el,"hookEndPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_hook_end_point);
}
if(strcasecmp(el,"talkStartPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_talk_start_point);
}
if(strcasecmp(el,"talkEndPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cut->cut_talk_end_point);
}
}
size_t __EditCutCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_EditCut(struct rd_cut *cut[],
struct edit_cut_values edit_cut_values,
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnum,
const unsigned cutnum,
const char user_agent[],
unsigned *numrecs)
{
char post[3500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/* Set number of recs so if fail already set */
*numrecs = 0;
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__EditCutElementStart,
__EditCutElementEnd);
XML_SetCharacterDataHandler(parser,__EditCutElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=15&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&CART_NUMBER=%u&CUT_NUMBER=%u",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
cartnum,
cutnum);
Build_Post_Cut_Fields(post, curl, edit_cut_values);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__EditCutCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) { //Success
*cut=xml_data.cut;
*numrecs = 1;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr,"rd_editcut Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}
void Build_Post_Cut_Fields(char *post, CURL *curl, struct edit_cut_values edit_values)
{
char buffer[1024];
char hold_datetime[34]; // take URL Encoding into account
int retlen=0;
/* Copy all of the applicable values into the post string */
if (edit_values.use_cut_evergreen)
{
snprintf(buffer,1024,"&EVERGREEN=%d",edit_values.cut_evergreen);
strcat(post,buffer);
}
if (edit_values.use_cut_description)
{
snprintf(buffer,1024,"&DESCRIPTION=%s",curl_easy_escape(curl,edit_values.cut_description,0));
strcat(post,buffer);
}
if (edit_values.use_cut_outcue)
{
snprintf(buffer,1024,"&OUTCUE=%s",curl_easy_escape(curl,edit_values.cut_outcue,0));
strcat(post,buffer);
}
if (edit_values.use_cut_isrc)
{
snprintf(buffer,1024,"&ISRC=%s",curl_easy_escape(curl,edit_values.cut_isrc,0));
strcat(post,buffer);
}
if (edit_values.use_cut_isci)
{
snprintf(buffer,1024,"&ISCI=%s",curl_easy_escape(curl,edit_values.cut_isci,0));
strcat(post,buffer);
}
if (edit_values.use_cut_start_datetime)
{
retlen = RD_Cnv_tm_to_DTString( &edit_values.cut_start_datetime,hold_datetime);
if (retlen > 0)
{
snprintf(buffer,1024,"&START_DATETIME=%s",hold_datetime);
strcat(post,buffer);
}
}
if (edit_values.use_cut_end_datetime)
{
retlen = RD_Cnv_tm_to_DTString( &edit_values.cut_end_datetime,hold_datetime);
if (retlen > 0)
{
snprintf(buffer,1024,"&END_DATETIME=%s",hold_datetime);
strcat(post,buffer);
}
}
if (edit_values.use_cut_sun)
{
snprintf(buffer,1024,"&SUN=%d",edit_values.cut_sun);
strcat(post,buffer);
}
if (edit_values.use_cut_mon)
{
snprintf(buffer,1024,"&MON=%d",edit_values.cut_mon);
strcat(post,buffer);
}
if (edit_values.use_cut_tue)
{
snprintf(buffer,1024,"&TUE=%d",edit_values.cut_tue);
strcat(post,buffer);
}
if (edit_values.use_cut_wed)
{
snprintf(buffer,1024,"&WED=%d",edit_values.cut_wed);
strcat(post,buffer);
}
if (edit_values.use_cut_thu)
{
snprintf(buffer,1024,"&THU=%d",edit_values.cut_thu);
strcat(post,buffer);
}
if (edit_values.use_cut_fri)
{
snprintf(buffer,1024,"&FRI=%d",edit_values.cut_fri);
strcat(post,buffer);
}
if (edit_values.use_cut_sat)
{
snprintf(buffer,1024,"&SAT=%d",edit_values.cut_sat);
strcat(post,buffer);
}
if (edit_values.use_cut_start_daypart)
{
snprintf(buffer,1024,"&START_DAYPART=%s",curl_easy_escape(curl,edit_values.cut_start_daypart,0));
strcat(post,buffer);
}
if (edit_values.use_cut_end_daypart)
{
snprintf(buffer,1024,"&END_DAYPART=%s",curl_easy_escape(curl,edit_values.cut_end_daypart,0));
strcat(post,buffer);
}
if (edit_values.use_cut_weight)
{
snprintf(buffer,1024,"&WEIGHT=%u",edit_values.cut_weight);
strcat(post,buffer);
}
if (edit_values.use_cut_validity)
{
snprintf(buffer,1024,"&VALIDITY=%u",edit_values.cut_validity);
strcat(post,buffer);
}
if (edit_values.use_cut_coding_format)
{
snprintf(buffer,1024,"&CODING_FORMAT=%u",edit_values.cut_coding_format);
strcat(post,buffer);
}
if (edit_values.use_cut_sample_rate)
{
snprintf(buffer,1024,"&SAMPLE_RATE=%u",edit_values.cut_sample_rate);
strcat(post,buffer);
}
if (edit_values.use_cut_bit_rate)
{
snprintf(buffer,1024,"&BIT_RATE=%u",edit_values.cut_bit_rate);
strcat(post,buffer);
}
if (edit_values.use_cut_channels)
{
snprintf(buffer,1024,"&CHANNELS=%u",edit_values.cut_channels);
strcat(post,buffer);
}
if (edit_values.use_cut_play_gain)
{
snprintf(buffer,1024,"&PLAY_GAIN=%d",edit_values.cut_play_gain);
strcat(post,buffer);
}
if (edit_values.use_cut_start_point)
{
snprintf(buffer,1024,"&START_POINT=%d",edit_values.cut_start_point);
strcat(post,buffer);
}
if (edit_values.use_cut_end_point)
{
snprintf(buffer,1024,"&END_POINT=%d",edit_values.cut_end_point);
strcat(post,buffer);
}
if (edit_values.use_cut_fadeup_point)
{
snprintf(buffer,1024,"&FADEUP_POINT=%d",edit_values.cut_fadeup_point);
strcat(post,buffer);
}
if (edit_values.use_cut_fadedown_point)
{
snprintf(buffer,1024,"&FADEDOWN_POINT=%d",edit_values.cut_fadedown_point);
strcat(post,buffer);
}
if (edit_values.use_cut_segue_start_point)
{
snprintf(buffer,1024,"&SEGUE_START_POINT=%d",edit_values.cut_segue_start_point);
strcat(post,buffer);
}
if (edit_values.use_cut_segue_end_point)
{
snprintf(buffer,1024,"&SEGUE_END_POINT=%d",edit_values.cut_segue_end_point);
strcat(post,buffer);
}
if (edit_values.use_cut_segue_gain)
{
snprintf(buffer,1024,"&SEGUE_GAIN=%d",edit_values.cut_segue_gain);
strcat(post,buffer);
}
if (edit_values.use_cut_hook_start_point)
{
snprintf(buffer,1024,"&HOOK_START_POINT=%d",edit_values.cut_hook_start_point);
strcat(post,buffer);
}
if (edit_values.use_cut_hook_end_point)
{
snprintf(buffer,1024,"&HOOK_END_POINT=%d",edit_values.cut_hook_end_point);
strcat(post,buffer);
}
if (edit_values.use_cut_talk_start_point)
{
snprintf(buffer,1024,"&TALK_START_POINT=%d",edit_values.cut_talk_start_point);
strcat(post,buffer);
}
if (edit_values.use_cut_talk_end_point)
{
snprintf(buffer,1024,"&TALK_END_POINT=%d",edit_values.cut_talk_end_point);
strcat(post,buffer);
}
}

View File

@@ -0,0 +1,120 @@
/* rd_editcut.h
*
* Header for the Edit Cut Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_EDITCUT_H
#define RD_EDITCUT_H
#include <rivwebcapi/rd_common.h>
#include <curl/curl.h>
_MYRIVLIB_INIT_DECL
#include <rivwebcapi/rd_cut.h>
struct edit_cut_values {
int cut_evergreen;
int use_cut_evergreen;
char cut_description[65];
int use_cut_description;
char cut_outcue[65];
int use_cut_outcue;
char cut_isrc[13];
int use_cut_isrc;
char cut_isci[33];
int use_cut_isci;
struct tm cut_start_datetime;
int use_cut_start_datetime;
struct tm cut_end_datetime;
int use_cut_end_datetime;
int cut_sun;
int use_cut_sun;
int cut_mon;
int use_cut_mon;
int cut_tue;
int use_cut_tue;
int cut_wed;
int use_cut_wed;
int cut_thu;
int use_cut_thu;
int cut_fri;
int use_cut_fri;
int cut_sat;
int use_cut_sat;
char cut_start_daypart[15];
int use_cut_start_daypart;
char cut_end_daypart[15];
int use_cut_end_daypart;
unsigned cut_weight;
int use_cut_weight;
unsigned cut_validity;
int use_cut_validity;
unsigned cut_coding_format;
int use_cut_coding_format;
unsigned cut_sample_rate;
int use_cut_sample_rate;
unsigned cut_bit_rate;
int use_cut_bit_rate;
unsigned cut_channels;
int use_cut_channels;
int cut_play_gain;
int use_cut_play_gain;
int cut_start_point;
int use_cut_start_point;
int cut_end_point;
int use_cut_end_point;
int cut_fadeup_point;
int use_cut_fadeup_point;
int cut_fadedown_point;
int use_cut_fadedown_point;
int cut_segue_start_point;
int use_cut_segue_start_point;
int cut_segue_end_point;
int use_cut_segue_end_point;
int cut_segue_gain;
int use_cut_segue_gain;
int cut_hook_start_point;
int use_cut_hook_start_point;
int cut_hook_end_point;
int use_cut_hook_end_point;
int cut_talk_start_point;
int use_cut_talk_start_point;
int cut_talk_end_point;
int use_cut_talk_end_point;
};
int RD_EditCut(struct rd_cut *cut[],
struct edit_cut_values edit_cut_values,
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnum,
const unsigned cutnum,
const char user_agent[],
unsigned *numrecs);
void Build_Post_Cut_Fields(char *post, CURL * curl, struct edit_cut_values edit_values);
_MYRIVLIB_FINI_DECL
#endif // RD_EDITCUT_H

View File

@@ -0,0 +1,164 @@
/* rd_export.c
*
* Implementation of the Export Cart Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include "rd_common.h"
#include "rd_getuseragent.h"
#include "rd_export.h"
size_t write_data( void *ptr, size_t size, size_t nmemb, FILE *stream)
{
size_t written;
written = fwrite(ptr,size,nmemb,stream);
return written;
}
int RD_ExportCart( const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnum,
const unsigned cutnum,
const int format,
const int channels,
const int sample_rate,
const int bit_rate,
const int quality,
const int start_point,
const int end_point,
const int normalization_level,
const int enable_metadata,
const char filename[],
const char user_agent[])
{
char post[1500];
char url[1500];
CURL *curl=NULL;
FILE *fp;
long response_code;
char *fnameptr;
char checked_fname[BUFSIZ];
int i;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* Check File name */
memset(checked_fname,'\0',sizeof(checked_fname));
fnameptr=&checked_fname[0];
for (i = 0 ; i < strlen(filename) ; i++) {
if (filename[i]>32) {
strncpy(fnameptr,&filename[i],1);
fnameptr++;
}
}
//
// Generate POST Data
//
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=1&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&CART_NUMBER=%u&CUT_NUMBER=%u&FORMAT=%d&CHANNELS=%d&SAMPLE_RATE=%d&BIT_RATE=%d&QUALITY=%d&START_POINT=%d&END_POINT=%d&NORMALIZATION_LEVEL=%d&ENABLE_METADATA=%d",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
cartnum,
cutnum,
format,
channels,
sample_rate,
bit_rate,
quality,
start_point,
end_point,
normalization_level,
enable_metadata);
/*
* Setup the CURL call
*/
fp = fopen(checked_fname,"wb");
if (!fp)
{
#ifdef RIVC_DEBUG_OUT
fprintf(stderr,"Error Opening Destination File\n");
#endif
curl_easy_cleanup(curl);
return -1;
}
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
curl_easy_setopt(curl,CURLOPT_URL, url);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,write_data);
curl_easy_setopt(curl,CURLOPT_WRITEDATA,fp);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_VERBOSE,0);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
fclose(fp);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) { //Success
return 0;
}
else
return (int)response_code;
}

View File

@@ -0,0 +1,49 @@
/* rd_export.h
*
* Header for the Edit Cart Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_EXPORT_H
#define RD_EXPORT_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
int RD_ExportCart(const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnum,
const unsigned cutnum,
const int format,
const int channels,
const int sample_rate,
const int bit_rate,
const int quality,
const int start_point,
const int end_point,
const int normalization_level,
const int enable_metadata,
const char filename[],
const char user_agent[]);
_MYRIVLIB_FINI_DECL
#endif // RD_EXPORT_H

View File

@@ -0,0 +1,147 @@
/* rd_exportpeaks.c
*
* Implementation of the Export Peaks Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include "rd_exportpeaks.h"
#include "rd_getuseragent.h"
#include "rd_common.h"
size_t __ExportPeaks_write_peaks_data( void *ptr, size_t size, size_t nmemb, FILE *stream)
{
size_t written;
written = fwrite(ptr,size,nmemb,stream);
return written;
}
int RD_ExportPeaks( const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnum,
const unsigned cutnum,
const char filename[],
const char user_agent[])
{
char post[1500];
char url[1500];
CURL *curl=NULL;
FILE *fp;
long response_code;
char *fnameptr;
char checked_fname[BUFSIZ];
int i;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* Check File name */
memset(checked_fname,'\0',sizeof(checked_fname));
fnameptr=&checked_fname[0];
for (i = 0 ; i < strlen(filename) ; i++) {
if (filename[i]>32) {
strncpy(fnameptr,&filename[i],1);
fnameptr++;
}
}
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
//
// Generate POST Data
//
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=16&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&CART_NUMBER=%u&CUT_NUMBER=%u",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
cartnum,
cutnum);
/*
* Setup the CURL call
*/
fp = fopen(checked_fname,"wb");
if (!fp)
{
#ifdef RIVC_DEBUG_OUT
fprintf(stderr,"Error Opening Destination File\n");
#endif
curl_easy_cleanup(curl);
return -1;
}
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
curl_easy_setopt(curl,CURLOPT_URL, url);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__ExportPeaks_write_peaks_data);
curl_easy_setopt(curl,CURLOPT_WRITEDATA,fp);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_VERBOSE,0);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
fclose(fp);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) { //Success
return 0;
}
else
return (int)response_code;
}

View File

@@ -0,0 +1,40 @@
/* rd_exportpeaks.h
*
* Header for the Export Peaks Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_EXPORTPEAKS_H
#define RD_EXPORTPEAKS_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
int RD_ExportPeaks(const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnum,
const unsigned cutnum,
const char filename[],
const char user_agent[]);
_MYRIVLIB_FINI_DECL
#endif // RD_EXPORTPEAKS_H

View File

@@ -0,0 +1,30 @@
/* rd_getuseragent.c
*
* Implementation of the Get User Agent Module in Rivendell C API Library
*
* (C) Copyright 2017 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include "rd_common.h"
#include "rd_getuseragent.h"
char * RD_GetUserAgent()
{
return USER_AGENT_STRING;
}

View File

@@ -0,0 +1,35 @@
/* rd_getuseragent.h
*
* Header for the Get User Agent Rivendell Access Library
*
* (C) Copyright 2017 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_GETUSERAGENT_H
#define RD_GETUSERAGENT_H
#include <rivwebcapi/rd_common.h>
#define USER_AGENT_STRING "rivwebcapi/"
_MYRIVLIB_INIT_DECL
char * RD_GetUserAgent();
_MYRIVLIB_FINI_DECL
#endif // RD_GETUSERAGENT_H

View File

@@ -0,0 +1,30 @@
/* rd_getversion.c
*
* Implementation of the Get Version Module in Rivendell C API Library
*
* (C) Copyright 2017 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include "rd_common.h"
#include "rd_getversion.h"
char * RD_GetVersion()
{
return VERSION;
}

View File

@@ -0,0 +1,33 @@
/* rd_getversion.h
*
* Header for the Get Version Rivendell Access Library
*
* (C) Copyright 2017 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_GETVERSION_H
#define RD_GETVERSION_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
char * RD_GetVersion();
_MYRIVLIB_FINI_DECL
#endif // RD_GETVERSION_H

View File

@@ -0,0 +1,34 @@
/* rd_group.h
*
* Header for the RD_GROUP Structure Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
*/
#ifndef RD_GROUP_H
#define RD_GROUP_H
struct rd_group {
char grp_name[11];
char grp_desc[255];
unsigned grp_default_cart_type;
unsigned grp_lo_limit;
unsigned grp_hi_limit;
int grp_shelf_life;
char grp_default_title[255];
int grp_enforce_range;
int grp_report_tfc;
int grp_report_mus;
int grp_now_next;
char grp_color[8];
char grp_reserved[457];
};
#endif // RD_GROUP_H

View File

@@ -0,0 +1,354 @@
/* rd_import.c
*
* Implementation of the Import Cart Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_import.h"
#include "rd_getuseragent.h"
#include "rd_common.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
struct rd_cartimport *cartimport;
};
static void XMLCALL __ImportCartElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
// Always allocate - because even if error we want to get error string
// if(strcasecmp(el,"RDWebResult")==0) { // Allocate a new cart entry
//
xml_data->cartimport=realloc(xml_data->cartimport, sizeof(struct rd_cartimport));
//}
strncpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __ImportCartElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __ImportCartElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_cartimport *cartimport=xml_data->cartimport;
if(strcasecmp(el,"CartNumber")==0) {
sscanf(xml_data->strbuf,"%u",&cartimport->cart_number);
}
if(strcasecmp(el,"CutNumber")==0) {
sscanf(xml_data->strbuf,"%u",&cartimport->cut_number);
}
if(strcasecmp(el,"ErrorString")==0) {
strlcpy(cartimport->error_string,xml_data->strbuf,256);
}
}
size_t __ImportCartCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_ImportCart(struct rd_cartimport *cartimport[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnum,
const unsigned cutnum,
const unsigned channels,
const int normalization_level,
const int autotrim_level,
const int use_metadata,
const int create,
const char group[],
const char title[],
const char filename[],
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
struct curl_httppost *first=NULL;
struct curl_httppost *last=NULL;
char *arrayptr;
char checked_fname[BUFSIZ];
int i;
char cart_buffer[50];
char cut_buffer[50];
char channels_buffer[50];
char normalization_buffer[50];
char autotrim_buffer[50];
char use_metadata_buffer[50];
char create_flag[50];
char checked_group_name[50];
long userlen = strlen(username);
long passwdlen = strlen(passwd);
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* Check File name */
memset(checked_fname,'\0',sizeof(checked_fname));
arrayptr=&checked_fname[0];
for (i = 0 ; i < strlen(filename) ; i++) {
if (filename[i]>32) {
strncpy(arrayptr,&filename[i],1);
arrayptr++;
}
}
/* Check Group Name */
memset(checked_group_name,'\0',sizeof(checked_group_name));
arrayptr=&checked_group_name[0];
for (i = 0 ; i < strlen(group) ; i++) {
if (group[i]>32) {
strncpy(arrayptr,&group[i],1);
arrayptr++;
}
}
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
//
// Generate POST Data
//
// We have to use multipart here because we have a file to send.
//
curl_formadd(&first,
&last,
CURLFORM_PTRNAME,
"COMMAND",
CURLFORM_COPYCONTENTS,
"2",
CURLFORM_END);
curl_formadd(&first,
&last,
CURLFORM_PTRNAME,
"LOGIN_NAME",
CURLFORM_COPYCONTENTS,
username,
CURLFORM_END);
curl_formadd(&first,
&last,
CURLFORM_PTRNAME,
"PASSWORD",
CURLFORM_COPYCONTENTS,
passwd,
CURLFORM_END);
curl_formadd(&first,
&last,
CURLFORM_PTRNAME,
"TICKET",
CURLFORM_COPYCONTENTS,
ticket,
CURLFORM_END);
sprintf(cart_buffer,"%u",cartnum);
curl_formadd(&first,
&last,
CURLFORM_PTRNAME,
"CART_NUMBER",
CURLFORM_COPYCONTENTS,
cart_buffer,
CURLFORM_END);
sprintf(cut_buffer,"%u",cutnum);
curl_formadd(&first,
&last,
CURLFORM_PTRNAME,
"CUT_NUMBER",
CURLFORM_COPYCONTENTS,
cut_buffer,
CURLFORM_END);
sprintf(channels_buffer,"%u",channels);
curl_formadd(&first,
&last,
CURLFORM_PTRNAME,
"CHANNELS",
CURLFORM_COPYCONTENTS,
channels_buffer,
CURLFORM_END);
sprintf(normalization_buffer,"%d",normalization_level);
curl_formadd(&first,
&last,
CURLFORM_PTRNAME,
"NORMALIZATION_LEVEL",
CURLFORM_COPYCONTENTS,
normalization_buffer,
CURLFORM_END);
sprintf(autotrim_buffer,"%d",autotrim_level);
curl_formadd(&first,
&last,
CURLFORM_PTRNAME,
"AUTOTRIM_LEVEL",
CURLFORM_COPYCONTENTS,
autotrim_buffer,
CURLFORM_END);
sprintf(use_metadata_buffer,"%d",use_metadata);
curl_formadd(&first,
&last,
CURLFORM_PTRNAME,
"USE_METADATA",
CURLFORM_COPYCONTENTS,
use_metadata_buffer,
CURLFORM_END);
sprintf(create_flag,"%d",create);
curl_formadd(&first,
&last,
CURLFORM_PTRNAME,
"CREATE",
CURLFORM_COPYCONTENTS,
create_flag,
CURLFORM_END);
curl_formadd(&first,
&last,
CURLFORM_PTRNAME,
"GROUP_NAME",
CURLFORM_COPYCONTENTS,
checked_group_name,
CURLFORM_END);
curl_formadd(&first,
&last,
CURLFORM_PTRNAME,
"TITLE",
CURLFORM_COPYCONTENTS,
title,
CURLFORM_END);
curl_formadd(&first,
&last,
CURLFORM_PTRNAME,
"FILENAME",
CURLFORM_FILE,
checked_fname,
CURLFORM_END);
/* Set number of recs so if fail already set */
*numrecs = 0;
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__ImportCartElementStart,
__ImportCartElementEnd);
XML_SetCharacterDataHandler(parser,__ImportCartElementData);
//curl_easy_setopt(curl, CURLOPT_WRITEDATA, stderr); Debug try
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_TIMEOUT,1200);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__ImportCartCallback);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_HTTPPOST,first);
curl_easy_setopt(curl,CURLOPT_VERBOSE,0);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_formfree(first);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
*cartimport=xml_data.cartimport;
*numrecs = 1;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_import Call Returned Error: %s\n",xml_data.strbuf);
#endif
*cartimport=xml_data.cartimport;
*numrecs = 0;
return (int)response_code;
}
}

View File

@@ -0,0 +1,56 @@
/* rd_import.h
*
* Header for the Import Cart Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_IMPORTCART_H
#define RD_IMPORTCART_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
struct rd_cartimport{
int response_code;
char error_string[256];
unsigned cart_number;
unsigned cut_number;
};
int RD_ImportCart(struct rd_cartimport *cartimport[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnum,
const unsigned cutnum,
const unsigned channels,
const int normalization_level,
const int autotrim_level,
const int use_metadata,
const int create,
const char group[],
const char title[],
const char filename[],
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_IMPORTCART_H

View File

@@ -0,0 +1,266 @@
/* rd_listcart.c
*
* Implementation of the ListCart Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_common.h"
#include "rd_getuseragent.h"
#include "rd_listcart.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
struct rd_cart *carts;
};
static void XMLCALL __ListCartElementStart(void *data, const char *el,
const char **attr)
{
unsigned i;
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"cart")==0) { // Allocate a new cart entry
xml_data->carts=realloc(xml_data->carts, sizeof(struct rd_cart));
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __ListCartElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __ListCartElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_cart *carts=xml_data->carts;
char hold_datetime[25];
if(strcasecmp(el,"number")==0) {
sscanf(xml_data->strbuf,"%u",&carts->cart_number);
}
if(strcasecmp(el,"type")==0) {
if(strcasecmp(xml_data->strbuf,"audio")==0) {
carts->cart_type=TYPE_AUDIO;
}
else {
if(strcasecmp(xml_data->strbuf,"macro")==0) {
carts->cart_type=TYPE_MACRO;
}
else
{
/* This is ALL type */
carts->cart_type=TYPE_ALL;
}
}
}
if(strcasecmp(el,"groupName")==0) {
strlcpy(carts->cart_grp_name,xml_data->strbuf,11);
}
if(strcasecmp(el,"title")==0) {
strlcpy(carts->cart_title,xml_data->strbuf,255);
}
if(strcasecmp(el,"artist")==0) {
strlcpy(carts->cart_artist,xml_data->strbuf,255);
}
if(strcasecmp(el,"album")==0) {
strlcpy(carts->cart_album,xml_data->strbuf,255);
}
if(strcasecmp(el,"year")==0) {
sscanf(xml_data->strbuf,"%d",&carts->cart_year);
}
if(strcasecmp(el,"label")==0) {
strlcpy(carts->cart_label,xml_data->strbuf,64);
}
if(strcasecmp(el,"client")==0) {
strlcpy(carts->cart_client,xml_data->strbuf,64);
}
if(strcasecmp(el,"agency")==0) {
strlcpy(carts->cart_agency,xml_data->strbuf,64);
}
if(strcasecmp(el,"publisher")==0) {
strlcpy(carts->cart_publisher,xml_data->strbuf,64);
}
if(strcasecmp(el,"composer")==0) {
strlcpy(carts->cart_composer,xml_data->strbuf,64);
}
if(strcasecmp(el,"conductor")==0) {
strlcpy(carts->cart_conductor,xml_data->strbuf,64);
}
if(strcasecmp(el,"userDefined")==0) {
strlcpy(carts->cart_user_defined,xml_data->strbuf,255);
}
if(strcasecmp(el,"usageCode")==0) {
sscanf(xml_data->strbuf,"%d",&carts->cart_usage_code);
}
if(strcasecmp(el,"forcedLength")==0) {
carts->cart_forced_length=RD_Cnv_TString_to_msec(xml_data->strbuf);
}
if(strcasecmp(el,"averageLength")==0) {
carts->cart_average_length=RD_Cnv_TString_to_msec(xml_data->strbuf);
}
if(strcasecmp(el,"lengthDeviation")==0) {
carts->cart_length_deviation=RD_Cnv_TString_to_msec(xml_data->strbuf);
}
if(strcasecmp(el,"averageSegueLength")==0) {
carts->cart_average_segue_length=RD_Cnv_TString_to_msec(xml_data->strbuf);
}
if(strcasecmp(el,"averageHookLength")==0) {
carts->cart_average_hook_length=RD_Cnv_TString_to_msec(xml_data->strbuf);
}
if(strcasecmp(el,"cutQuantity")==0) {
sscanf(xml_data->strbuf,"%u",&carts->cart_cut_quantity);
}
if(strcasecmp(el,"lastCutPlayed")==0) {
sscanf(xml_data->strbuf,"%u",&carts->cart_last_cut_played);
}
if(strcasecmp(el,"validity")==0) {
sscanf(xml_data->strbuf,"%u",&carts->cart_validity);
}
if(strcasecmp(el,"enforceLength")==0) {
carts->cart_enforce_length=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"asyncronous")==0) {
carts->cart_asyncronous=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"owner")==0) {
strlcpy(carts->cart_owner,xml_data->strbuf,66);
}
if(strcasecmp(el,"metadataDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
carts->cart_metadata_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
}
size_t __ListCartCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_ListCart(struct rd_cart *carts[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnumber,
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* Set number of recs so if fail already set */
*numrecs = 0;
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__ListCartElementStart,
__ListCartElementEnd);
XML_SetCharacterDataHandler(parser,__ListCartElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=7&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&CART_NUMBER=%u",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
cartnumber);
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__ListCartCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
*carts=xml_data.carts;
*numrecs = 1;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_listcart Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,42 @@
/* rd_listcart.h
*
* Header for the ListCart Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_LISTCART_H
#define RD_LISTCART_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
#include <rivwebcapi/rd_cart.h>
int RD_ListCart(struct rd_cart *carts[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnumber,
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_LISTCART_H

View File

@@ -0,0 +1,271 @@
/* rd_listcarts.c
*
* Implementation of the LastCarts Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_common.h"
#include "rd_getuseragent.h"
#include "rd_listcarts.h"
struct xml_data {
unsigned carts_quan;
char elem_name[256];
char strbuf[1024];
struct rd_cart *carts;
};
static void XMLCALL __ListCartsElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"cart")==0) { // Allocate a new cart entry
xml_data->carts=realloc(xml_data->carts,
(xml_data->carts_quan+1)*sizeof(struct rd_cart));
(xml_data->carts_quan)++;
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __ListCartsElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __ListCartsElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_cart *carts=xml_data->carts+(xml_data->carts_quan-1);
char hold_datetime[25];
if(strcasecmp(el,"number")==0) {
sscanf(xml_data->strbuf,"%u",&carts->cart_number);
}
if(strcasecmp(el,"type")==0) {
if(strcasecmp(xml_data->strbuf,"audio")==0) {
carts->cart_type=TYPE_AUDIO;
}
if(strcasecmp(xml_data->strbuf,"macro")==0) {
carts->cart_type=TYPE_MACRO;
}
else
{
/* This is ALL type */
carts->cart_type=TYPE_ALL;
}
}
if(strcasecmp(el,"groupName")==0) {
strlcpy(carts->cart_grp_name,xml_data->strbuf,11);
}
if(strcasecmp(el,"title")==0) {
strlcpy(carts->cart_title,xml_data->strbuf,256);
}
if(strcasecmp(el,"artist")==0) {
strlcpy(carts->cart_artist,xml_data->strbuf,256);
}
if(strcasecmp(el,"album")==0) {
strlcpy(carts->cart_album,xml_data->strbuf,256);
}
if(strcasecmp(el,"year")==0) {
sscanf(xml_data->strbuf,"%d",&carts->cart_year);
}
if(strcasecmp(el,"label")==0) {
strlcpy(carts->cart_label,xml_data->strbuf,65);
}
if(strcasecmp(el,"client")==0) {
strlcpy(carts->cart_client,xml_data->strbuf,65);
}
if(strcasecmp(el,"agency")==0) {
strlcpy(carts->cart_agency,xml_data->strbuf,65);
}
if(strcasecmp(el,"publisher")==0) {
strlcpy(carts->cart_publisher,xml_data->strbuf,65);
}
if(strcasecmp(el,"composer")==0) {
strlcpy(carts->cart_composer,xml_data->strbuf,65);
}
if(strcasecmp(el,"conductor")==0) {
strlcpy(carts->cart_conductor,xml_data->strbuf,65);
}
if(strcasecmp(el,"userDefined")==0) {
strlcpy(carts->cart_user_defined,xml_data->strbuf,256);
}
if(strcasecmp(el,"usageCode")==0) {
sscanf(xml_data->strbuf,"%d",&carts->cart_usage_code);
}
if(strcasecmp(el,"forcedLength")==0) {
carts->cart_forced_length=RD_Cnv_TString_to_msec(xml_data->strbuf);
}
if(strcasecmp(el,"averageLength")==0) {
carts->cart_average_length=RD_Cnv_TString_to_msec(xml_data->strbuf);
}
if(strcasecmp(el,"lengthDeviation")==0) {
carts->cart_length_deviation=RD_Cnv_TString_to_msec(xml_data->strbuf);
}
if(strcasecmp(el,"averageSegueLength")==0) {
carts->cart_average_segue_length=RD_Cnv_TString_to_msec(xml_data->strbuf);
}
if(strcasecmp(el,"averageHookLength")==0) {
carts->cart_average_hook_length=RD_Cnv_TString_to_msec(xml_data->strbuf);
}
if(strcasecmp(el,"cutQuantity")==0) {
sscanf(xml_data->strbuf,"%u",&carts->cart_cut_quantity);
}
if(strcasecmp(el,"lastCutPlayed")==0) {
sscanf(xml_data->strbuf,"%u",&carts->cart_last_cut_played);
}
if(strcasecmp(el,"validity")==0) {
sscanf(xml_data->strbuf,"%u",&carts->cart_validity);
}
if(strcasecmp(el,"enforceLength")==0) {
carts->cart_enforce_length=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"asyncronous")==0) {
carts->cart_asyncronous=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"owner")==0) {
strlcpy(carts->cart_owner,xml_data->strbuf,66);
}
if(strcasecmp(el,"metadataDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
carts->cart_metadata_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
}
size_t __ListCartsCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_ListCarts(struct rd_cart *carts[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char group_name[],
const char filter[],
const char type[],
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* Set number of recs so if fail already set */
*numrecs = 0;
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__ListCartsElementStart,
__ListCartsElementEnd);
XML_SetCharacterDataHandler(parser,__ListCartsElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=6&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&GROUP_NAME=%s&FILTER=%s&TYPE=%s",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
curl_easy_escape(curl,group_name,0),
curl_easy_escape(curl,filter,0),
curl_easy_escape(curl,type,0));
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__ListCartsCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
*carts=xml_data.carts;
*numrecs = xml_data.carts_quan;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_listcarts Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,44 @@
/* rd_listcarts.h
*
* Header for the ListCarts Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_LISTCARTS_H
#define RD_LISTCARTS_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
#include <rivwebcapi/rd_cart.h>
int RD_ListCarts(struct rd_cart *carts[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char group_name[],
const char filter[],
const char type[],
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_LISTCARTS_H

View File

@@ -0,0 +1,178 @@
/* rd_listcartschedulcodes.c
*
* Implementation of the ListCartSchedulCodes Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_listcartschedcodes.h"
#include "rd_common.h"
#include "rd_getuseragent.h"
struct xml_data {
unsigned schedcodes_quan;
char elem_name[256];
char strbuf[1024];
struct rd_schedcodes *schedcodes;
};
static void XMLCALL __ListCartSchedCodesElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"schedCode")==0) { // Allocate a new schedule code entry
xml_data->schedcodes=realloc(xml_data->schedcodes,
(xml_data->schedcodes_quan+1)*sizeof(struct rd_schedcodes));
(xml_data->schedcodes_quan)++;
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __ListCartSchedCodesElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __ListCartSchedCodesElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_schedcodes *schedcodes=xml_data->schedcodes+(xml_data->schedcodes_quan-1);
if(strcasecmp(el,"code")==0) {
strlcpy(schedcodes->code,xml_data->strbuf,10);
}
if(strcasecmp(el,"description")==0){
strlcpy(schedcodes->description,xml_data->strbuf,256);
}
}
size_t __ListCartSchedCodesCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_ListCartSchedCodes(struct rd_schedcodes *scodes[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnum,
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* Set number of recs so if fail already set */
*numrecs = 0;
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__ListCartSchedCodesElementStart,
__ListCartSchedCodesElementEnd);
XML_SetCharacterDataHandler(parser,__ListCartSchedCodesElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=27&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&CART_NUMBER=%u",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
cartnum);
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__ListCartSchedCodesCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
*scodes=xml_data.schedcodes;
*numrecs = xml_data.schedcodes_quan;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_listcartschedcodes Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,42 @@
/* rd_listcartschedcodes.h
*
* Header for the ListCartSchedulCodes Web Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_LISTCARTSCHEDCODES_H
#define RD_LISTCARTSCHEDCODES_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
#include <rivwebcapi/rd_schedcodes.h>
int RD_ListCartSchedCodes(struct rd_schedcodes *schedcodes[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnum,
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_LISTCARTSCHEDCODES_H

View File

@@ -0,0 +1,314 @@
/* rd_listcuts.c
*
* Implementation of the LastCuts Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_common.h"
#include "rd_getuseragent.h"
#include "rd_listcut.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
struct rd_cut *cuts;
};
static void XMLCALL __ListCutElementStart(void *data, const char *el,
const char **attr)
{
unsigned i;
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"cut")==0) { // Allocate a new cut entry
xml_data->cuts=realloc(xml_data->cuts,
sizeof(struct rd_cut));
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __ListCutElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __ListCutElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_cut *cuts=xml_data->cuts;
char hold_datetime[25];
if(strcasecmp(el,"cutName")==0) {
strlcpy(cuts->cut_name,xml_data->strbuf,11);
}
if(strcasecmp(el,"cartNumber")==0) {
sscanf(xml_data->strbuf,"%u",&cuts->cut_cart_number);
}
if(strcasecmp(el,"cutNumber")==0){
sscanf(xml_data->strbuf,"%u",&cuts->cut_cut_number);
}
if(strcasecmp(el,"evergreen")==0) {
cuts->cut_evergreen=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"description")==0) {
strlcpy(cuts->cut_description,xml_data->strbuf,65);
}
if(strcasecmp(el,"outcue")==0) {
strlcpy(cuts->cut_outcue,xml_data->strbuf,65);
}
if(strcasecmp(el,"isrc")==0) {
strlcpy(cuts->cut_isrc,xml_data->strbuf,13);
}
if(strcasecmp(el,"isci")==0) {
strlcpy(cuts->cut_isci,xml_data->strbuf,33);
}
if(strcasecmp(el,"length")==0){
sscanf(xml_data->strbuf,"%u",&cuts->cut_length);
}
if(strcasecmp(el,"originDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
cuts->cut_origin_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"startDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
cuts->cut_start_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"endDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
cuts->cut_end_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"sun")==0) {
cuts->cut_sun=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"mon")==0) {
cuts->cut_mon=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"tue")==0) {
cuts->cut_tue=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"wed")==0) {
cuts->cut_wed=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"thu")==0) {
cuts->cut_thu=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"fri")==0) {
cuts->cut_fri=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"sat")==0) {
cuts->cut_sat=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"startDaypart")==0) {
strlcpy(cuts->cut_start_daypart,xml_data->strbuf,15);
}
if(strcasecmp(el,"endDaypart")==0) {
strlcpy(cuts->cut_end_daypart,xml_data->strbuf,15);
}
if(strcasecmp(el,"originName")==0) {
strlcpy(cuts->cut_origin_name,xml_data->strbuf,65);
}
if(strcasecmp(el,"originLoginName")==0) {
strlcpy(cuts->cut_origin_login_name,xml_data->strbuf,256);
}
if(strcasecmp(el,"sourceHostname")==0) {
strlcpy(cuts->cut_source_hostname,xml_data->strbuf,256);
}
if(strcasecmp(el,"weight")==0) {
sscanf(xml_data->strbuf,"%u",&cuts->cut_weight);
}
if(strcasecmp(el,"lastPlayDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
cuts->cut_last_play_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"playCounter")==0) {
sscanf(xml_data->strbuf,"%u",&cuts->cut_play_counter);
}
if(strcasecmp(el,"localCounter")==0) {
sscanf(xml_data->strbuf,"%u",&cuts->cut_local_counter);
}
if(strcasecmp(el,"validity")==0) {
sscanf(xml_data->strbuf,"%u",&cuts->cut_validity);
}
if(strcasecmp(el,"codingFormat")==0) {
sscanf(xml_data->strbuf,"%u",&cuts->cut_coding_format);
}
if(strcasecmp(el,"sampleRate")==0) {
sscanf(xml_data->strbuf,"%u",&cuts->cut_sample_rate);
}
if(strcasecmp(el,"bitRate")==0) {
sscanf(xml_data->strbuf,"%u",&cuts->cut_bit_rate);
}
if(strcasecmp(el,"channels")==0) {
sscanf(xml_data->strbuf,"%u",&cuts->cut_channels);
}
if(strcasecmp(el,"playGain")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_play_gain);
}
if(strcasecmp(el,"startPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_start_point);
}
if(strcasecmp(el,"endPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_end_point);
}
if(strcasecmp(el,"fadeupPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_fadeup_point);
}
if(strcasecmp(el,"fadedownPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_fadedown_point);
}
if(strcasecmp(el,"segueStartPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_segue_start_point);
}
if(strcasecmp(el,"segueEndPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_segue_end_point);
}
if(strcasecmp(el,"segueGain")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_segue_gain);
}
if(strcasecmp(el,"hookStartPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_hook_start_point);
}
if(strcasecmp(el,"hookEndPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_hook_end_point);
}
if(strcasecmp(el,"talkStartPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_talk_start_point);
}
if(strcasecmp(el,"talkEndPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_talk_end_point);
}
}
size_t __ListCutCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_ListCut(struct rd_cut *cuts[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnumber,
const unsigned cutnumber,
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* Set number of recs so if fail already set */
*numrecs = 0;
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__ListCutElementStart,
__ListCutElementEnd);
XML_SetCharacterDataHandler(parser,__ListCutElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=8&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&CART_NUMBER=%u&CUT_NUMBER=%u",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
cartnumber,
cutnumber);
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__ListCutCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
*cuts=xml_data.cuts;
*numrecs = 1;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_listcut Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,43 @@
/* rd_listcuts.h
*
* Header for the ListCuts Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_LISTCUT_H
#define RD_LISTCUT_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
#include <rivwebcapi/rd_cut.h>
int RD_ListCut(struct rd_cut *cuts[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnumber,
const unsigned cutnumber,
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_LISTCUT_H

View File

@@ -0,0 +1,314 @@
/* rd_listcuts.c
*
* Implementation of the LastCuts Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_common.h"
#include "rd_getuseragent.h"
#include "rd_listcuts.h"
struct xml_data {
unsigned cuts_quan;
char elem_name[256];
char strbuf[1024];
struct rd_cut *cuts;
};
static void XMLCALL __ListCutsElementStart(void *data, const char *el,
const char **attr)
{
unsigned i;
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"cut")==0) { // Allocate a new cut entry
xml_data->cuts=realloc(xml_data->cuts,
(xml_data->cuts_quan+1)*sizeof(struct rd_cut));
(xml_data->cuts_quan)++;
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __ListCutsElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __ListCutsElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_cut *cuts=xml_data->cuts+(xml_data->cuts_quan-1);
char hold_datetime[26];
if(strcasecmp(el,"cutName")==0) {
strlcpy(cuts->cut_name,xml_data->strbuf,11);
}
if(strcasecmp(el,"cartNumber")==0) {
sscanf(xml_data->strbuf,"%u",&cuts->cut_cart_number);
}
if(strcasecmp(el,"cutNumber")==0){
sscanf(xml_data->strbuf,"%u",&cuts->cut_cut_number);
}
if(strcasecmp(el,"evergreen")==0) {
cuts->cut_evergreen=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"description")==0) {
strlcpy(cuts->cut_description,xml_data->strbuf,65);
}
if(strcasecmp(el,"outcue")==0) {
strlcpy(cuts->cut_outcue,xml_data->strbuf,65);
}
if(strcasecmp(el,"isrc")==0) {
strlcpy(cuts->cut_isrc,xml_data->strbuf,13);
}
if(strcasecmp(el,"isci")==0) {
strlcpy(cuts->cut_isci,xml_data->strbuf,33);
}
if(strcasecmp(el,"length")==0){
sscanf(xml_data->strbuf,"%u",&cuts->cut_length);
}
if(strcasecmp(el,"originDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
cuts->cut_origin_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"startDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
cuts->cut_start_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"endDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
cuts->cut_end_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"sun")==0) {
cuts->cut_sun=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"mon")==0) {
cuts->cut_mon=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"tue")==0) {
cuts->cut_tue=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"wed")==0) {
cuts->cut_wed=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"thu")==0) {
cuts->cut_thu=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"fri")==0) {
cuts->cut_fri=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"sat")==0) {
cuts->cut_sat=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"startDaypart")==0) {
strlcpy(cuts->cut_start_daypart,xml_data->strbuf,10);
}
if(strcasecmp(el,"endDaypart")==0) {
strlcpy(cuts->cut_end_daypart,xml_data->strbuf,10);
}
if(strcasecmp(el,"originName")==0) {
strlcpy(cuts->cut_origin_name,xml_data->strbuf,65);
}
if(strcasecmp(el,"originLoginName")==0) {
strlcpy(cuts->cut_origin_login_name,xml_data->strbuf,256);
}
if(strcasecmp(el,"sourceHostname")==0) {
strlcpy(cuts->cut_source_hostname,xml_data->strbuf,256);
}
if(strcasecmp(el,"weight")==0) {
sscanf(xml_data->strbuf,"%u",&cuts->cut_weight);
}
if(strcasecmp(el,"lastPlayDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
cuts->cut_last_play_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"playCounter")==0) {
sscanf(xml_data->strbuf,"%u",&cuts->cut_play_counter);
}
if(strcasecmp(el,"localCounter")==0) {
sscanf(xml_data->strbuf,"%u",&cuts->cut_local_counter);
}
if(strcasecmp(el,"validity")==0) {
sscanf(xml_data->strbuf,"%u",&cuts->cut_validity);
}
if(strcasecmp(el,"codingFormat")==0) {
sscanf(xml_data->strbuf,"%u",&cuts->cut_coding_format);
}
if(strcasecmp(el,"sampleRate")==0) {
sscanf(xml_data->strbuf,"%u",&cuts->cut_sample_rate);
}
if(strcasecmp(el,"bitRate")==0) {
sscanf(xml_data->strbuf,"%u",&cuts->cut_bit_rate);
}
if(strcasecmp(el,"channels")==0) {
sscanf(xml_data->strbuf,"%u",&cuts->cut_channels);
}
if(strcasecmp(el,"playGain")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_play_gain);
}
if(strcasecmp(el,"startPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_start_point);
}
if(strcasecmp(el,"endPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_end_point);
}
if(strcasecmp(el,"fadeupPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_fadeup_point);
}
if(strcasecmp(el,"fadedownPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_fadedown_point);
}
if(strcasecmp(el,"segueStartPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_segue_start_point);
}
if(strcasecmp(el,"segueEndPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_segue_end_point);
}
if(strcasecmp(el,"segueGain")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_segue_gain);
}
if(strcasecmp(el,"hookStartPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_hook_start_point);
}
if(strcasecmp(el,"hookEndPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_hook_end_point);
}
if(strcasecmp(el,"talkStartPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_talk_start_point);
}
if(strcasecmp(el,"talkEndPoint")==0) {
sscanf(xml_data->strbuf,"%d",&cuts->cut_talk_end_point);
}
}
size_t __ListCutsCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_ListCuts(struct rd_cut *cuts[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnumber,
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* Set number of recs so if fail already set */
*numrecs = 0;
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__ListCutsElementStart,
__ListCutsElementEnd);
XML_SetCharacterDataHandler(parser,__ListCutsElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=9&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&CART_NUMBER=%u",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
cartnumber);
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__ListCutsCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
*cuts=xml_data.cuts;
*numrecs = xml_data.cuts_quan;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_listcuts Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,42 @@
/* rd_listcuts.h
*
* Header for the ListCuts Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_LISTCUTS_H
#define RD_LISTCUTS_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
#include <rivwebcapi/rd_cut.h>
int RD_ListCuts(struct rd_cut *cuts[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnumber,
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_LISTCUTS_H

View File

@@ -0,0 +1,208 @@
/* rd_listgroup.c
*
* Implementation of the ListGroup Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_common.h"
#include "rd_getuseragent.h"
#include "rd_listgroup.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
struct rd_group *group;
};
static void XMLCALL __ListGroupElementStart(void *data, const char *el,
const char **attr)
{
unsigned i;
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"group")==0) { // Allocate a new group entry
xml_data->group=realloc(xml_data->group, sizeof(struct rd_group));
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __ListGroupElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __ListGroupElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_group *grp=xml_data->group;
if(strcasecmp(el,"name")==0) {
strlcpy(grp->grp_name,xml_data->strbuf,10);
}
if(strcasecmp(el,"description")==0) {
strlcpy(grp->grp_desc,xml_data->strbuf,255);
}
if(strcasecmp(el,"defaultcarttype")==0) {
if(strcasecmp(xml_data->strbuf,"audio")==0) {
grp->grp_default_cart_type=0;
}
if(strcasecmp(xml_data->strbuf,"macro")==0) {
grp->grp_default_cart_type=1;
}
}
if(strcasecmp(el,"defaultlowcart")==0) {
sscanf(xml_data->strbuf,"%u",&grp->grp_lo_limit);
}
if(strcasecmp(el,"defaulthighcart")==0) {
sscanf(xml_data->strbuf,"%u",&grp->grp_hi_limit);
}
if(strcasecmp(el,"cutshelflife")==0) {
sscanf(xml_data->strbuf,"%d",&grp->grp_shelf_life);
}
if(strcasecmp(el,"defaulttitle")==0) {
strlcpy(grp->grp_default_title,xml_data->strbuf,255);
}
if(strcasecmp(el,"enforcecartrange")==0) {
grp->grp_enforce_range=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"reporttfc")==0) {
grp->grp_report_tfc=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"reportmus")==0) {
grp->grp_report_mus=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"color")==0) {
strlcpy(grp->grp_color,xml_data->strbuf,8);
}
}
size_t __ListGroupCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_ListGroup(struct rd_group *grp[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char groupname[],
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* set number of recs so if fail already set */
*numrecs = 0;
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__ListGroupElementStart,
__ListGroupElementEnd);
XML_SetCharacterDataHandler(parser,__ListGroupElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=5&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&GROUP_NAME=%s",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
curl_easy_escape(curl,groupname,0));
//
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__ListGroupCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
*grp=xml_data.group;
*numrecs = 1;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_listgroup Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,42 @@
/* rd_listgroup.h
*
* Header for the ListGroups Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_LISTGROUP_H
#define RD_LISTGROUP_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
#include <rivwebcapi/rd_group.h>
int RD_ListGroup(struct rd_group *grp[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char group[],
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_LISTGROUP_H

View File

@@ -0,0 +1,209 @@
/* rd_listgroups.c
*
* Implementation of the ListGroups Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_common.h"
#include "rd_getuseragent.h"
#include "rd_listgroups.h"
struct xml_data {
unsigned grps_quan;
char elem_name[256];
char strbuf[1024];
struct rd_group *grps;
};
static void XMLCALL __ListGroupsElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"group")==0) { // Allocate a new group entry
xml_data->grps=realloc(xml_data->grps,
(xml_data->grps_quan+1)*sizeof(struct rd_group));
(xml_data->grps_quan)++;
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __ListGroupsElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __ListGroupsElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_group *grp=xml_data->grps+(xml_data->grps_quan-1);
if(strcasecmp(el,"name")==0) {
strlcpy(grp->grp_name,xml_data->strbuf,10);
}
if(strcasecmp(el,"description")==0) {
strlcpy(grp->grp_desc,xml_data->strbuf,256);
}
if(strcasecmp(el,"defaultcarttype")==0) {
if(strcasecmp(xml_data->strbuf,"audio")==0) {
grp->grp_default_cart_type=0;
}
if(strcasecmp(xml_data->strbuf,"macro")==0) {
grp->grp_default_cart_type=1;
}
}
if(strcasecmp(el,"defaultlowcart")==0) {
sscanf(xml_data->strbuf,"%u",&grp->grp_lo_limit);
}
if(strcasecmp(el,"defaulthighcart")==0) {
sscanf(xml_data->strbuf,"%u",&grp->grp_hi_limit);
}
if(strcasecmp(el,"cutshelflife")==0) {
sscanf(xml_data->strbuf,"%d",&grp->grp_shelf_life);
}
if(strcasecmp(el,"defaulttitle")==0) {
strlcpy(grp->grp_default_title,xml_data->strbuf,256);
}
if(strcasecmp(el,"enforcecartrange")==0) {
grp->grp_enforce_range=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"reporttfc")==0) {
grp->grp_report_tfc=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"reportmus")==0) {
grp->grp_report_mus=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"color")==0) {
strlcpy(grp->grp_color,xml_data->strbuf,8);
}
}
size_t __ListGroupsCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_ListGroups(struct rd_group *grps[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
struct rd_group groups[20];
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* set number of recs so if fail already set */
*numrecs = 0;
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__ListGroupsElementStart,
__ListGroupsElementEnd);
XML_SetCharacterDataHandler(parser,__ListGroupsElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=4&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0));
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__ListGroupsCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
*grps=xml_data.grps;
*numrecs = xml_data.grps_quan;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_listgroups Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,41 @@
/* rd_listgroups.h
*
* Header for the ListGroups Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_LISTGROUPS_H
#define RD_LISTGROUPS_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
#include <rivwebcapi/rd_group.h>
int RD_ListGroups(struct rd_group *grps[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_LISTGROUPS_H

View File

@@ -0,0 +1,525 @@
/* rd_listlog.c
*
* Implementation of the ListLog Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_common.h"
#include "rd_getuseragent.h"
#include "rd_listlog.h"
struct xml_data {
unsigned logline_quan;
char elem_name[256];
char attribute[256];
char attribute_value[256];
char strbuf[1024];
struct rd_logline *logline;
};
static void XMLCALL __ListLogElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"logLine")==0) { // Allocate a new logline entry
xml_data->logline=realloc(xml_data->logline,
(xml_data->logline_quan+1)*sizeof(struct rd_logline));
(xml_data->logline_quan)++;
}
if (attr[0]) {
strcpy(xml_data->attribute,attr[0]);
strcpy(xml_data->attribute_value,attr[1]);
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __ListLogElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __ListLogElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_logline *logline=xml_data->logline+(xml_data->logline_quan-1);
char hold_datetime[26];
if(strcasecmp(el,"line")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_line);
}
if(strcasecmp(el,"id")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_id);
}
if(strcasecmp(el,"type")==0) {
if(strcasecmp(xml_data->strbuf,"Audio")==0) {
logline->logline_type=0;
}
if(strcasecmp(xml_data->strbuf,"Marker")==0) {
logline->logline_type=1;
}
if(strcasecmp(xml_data->strbuf,"Macro")==0) {
logline->logline_type=2;
}
if(strcasecmp(xml_data->strbuf,"OpenBracket")==0) {
logline->logline_type=3;
}
if(strcasecmp(xml_data->strbuf,"CloseBracket")==0) {
logline->logline_type=4;
}
if(strcasecmp(xml_data->strbuf,"Chain")==0) {
logline->logline_type=5;
}
if(strcasecmp(xml_data->strbuf,"Track")==0) {
logline->logline_type=6;
}
if(strcasecmp(xml_data->strbuf,"MusicLink")==0) {
logline->logline_type=7;
}
if(strcasecmp(xml_data->strbuf,"TrafficLink")==0) {
logline->logline_type=8;
}
if(strcasecmp(xml_data->strbuf,"UnknownType")==0) {
logline->logline_type=9;
}
}
if(strcasecmp(el,"cartType")==0) {
if(strcasecmp(xml_data->strbuf,"Audio")==0) {
logline->logline_cart_type=1;
}
else {
if(strcasecmp(xml_data->strbuf,"Macro")==0) {
logline->logline_cart_type=2;
}
else
{
/* This is ALL type */
logline->logline_cart_type=0;
}
}
}
if(strcasecmp(el,"cartNumber")==0){
sscanf(xml_data->strbuf,"%u",&logline->logline_cart_number);
}
if(strcasecmp(el,"cutNumber")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_cut_number);
}
if(strcasecmp(el,"groupName")==0) {
strlcpy(logline->logline_group_name,xml_data->strbuf,10);
}
if(strcasecmp(el,"groupColor")==0) {
sscanf(xml_data->strbuf,"%s",(char *)&logline->logline_group_color);
}
if(strcasecmp(el,"title")==0) {
strlcpy(logline->logline_title,xml_data->strbuf,256);
}
if(strcasecmp(el,"artist")==0) {
strlcpy(logline->logline_artist,xml_data->strbuf,256);
}
if(strcasecmp(el,"publisher")==0) {
strlcpy(logline->logline_publisher,xml_data->strbuf,65);
}
if(strcasecmp(el,"composer")==0) {
strlcpy(logline->logline_composer,xml_data->strbuf,65);
}
if(strcasecmp(el,"album")==0) {
strlcpy(logline->logline_album,xml_data->strbuf,256);
}
if(strcasecmp(el,"label")==0) {
strlcpy(logline->logline_label,xml_data->strbuf,65);
}
if(strcasecmp(el,"year")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_year);
}
if(strcasecmp(el,"client")==0) {
strlcpy(logline->logline_client,xml_data->strbuf,65);
}
if(strcasecmp(el,"agency")==0) {
strlcpy(logline->logline_agency,xml_data->strbuf,65);
}
if(strcasecmp(el,"conductor")==0) {
strlcpy(logline->logline_conductor,xml_data->strbuf,65);
}
if(strcasecmp(el,"userDefined")==0) {
strlcpy(logline->logline_user_defined,xml_data->strbuf,256);
}
if(strcasecmp(el,"usageCode")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_usage_code);
}
if(strcasecmp(el,"enforceLength")==0) {
logline->logline_enforce_length=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"forcedLength")==0) {
logline->logline_forced_length=RD_Cnv_TString_to_msec(xml_data->strbuf);
}
if(strcasecmp(el,"evergreen")==0) {
logline->logline_evergreen=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"source")==0) {
if(strcasecmp(xml_data->strbuf,"Manual")==0) {
logline->logline_source=0;
}
if(strcasecmp(xml_data->strbuf,"Traffic")==0) {
logline->logline_source=1;
}
if(strcasecmp(xml_data->strbuf,"Music")==0) {
logline->logline_source=2;
}
if(strcasecmp(xml_data->strbuf,"Template")==0) {
logline->logline_source=3;
}
if(strcasecmp(xml_data->strbuf,"Tracker")==0) {
logline->logline_source=4;
}
}
if(strcasecmp(el,"timeType")==0) {
if(strcasecmp(xml_data->strbuf,"Relative")==0) {
logline->logline_time_type=0;
}
if(strcasecmp(xml_data->strbuf,"Hard")==0) {
logline->logline_time_type=1;
}
if(strcasecmp(xml_data->strbuf,"NoTime")==0) {
logline->logline_time_type=255;
}
}
if(strcasecmp(el,"startTime")==0) {
logline->logline_starttime=RD_Cnv_TString_to_msec(xml_data->strbuf);
}
if(strcasecmp(el,"transitionType")==0) {
if(strcasecmp(xml_data->strbuf,"PLAY")==0) {
logline->logline_transition_type=0;
}
else {
if(strcasecmp(xml_data->strbuf,"SEGUE")==0) {
logline->logline_transition_type=1;
}
else {
if(strcasecmp(xml_data->strbuf,"STOP")==0) {
logline->logline_transition_type=2;
}
else {
logline->logline_transition_type=255;
}
}
}
}
if(strcasecmp(el,"cutQuantity")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_cut_quantity);
}
if(strcasecmp(el,"lastCutPlayed")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_last_cut_played);
}
if(strcasecmp(el,"markerComment")==0) {
strlcpy(logline->logline_marker_comment,xml_data->strbuf,256);
}
if(strcasecmp(el,"markerLabel")==0) {
strlcpy(logline->logline_marker_label,xml_data->strbuf,65);
}
if(strcasecmp(el,"originUser")==0) {
sscanf(xml_data->strbuf,"%s",(char *)&logline->logline_origin_user);
}
if(strcasecmp(el,"originDateTime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
logline->logline_origin_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"startPoint")==0) {
if(strcasecmp(xml_data->attribute,"src")==0) {
if(strcasecmp(xml_data->attribute_value,"cart")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_start_point_cart);
}
else {
if(strcasecmp(xml_data->attribute_value,"log")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_start_point_log);
}
}
}
}
if(strcasecmp(el,"endPoint")==0) {
if(strcasecmp(xml_data->attribute,"src")==0) {
if(strcasecmp(xml_data->attribute_value,"cart")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_end_point_cart);
}
else {
if(strcasecmp(xml_data->attribute_value,"log")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_end_point_log);
}
}
}
}
if(strcasecmp(el,"segueStartPoint")==0) {
if(strcasecmp(xml_data->attribute,"src")==0) {
if(strcasecmp(xml_data->attribute_value,"cart")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_segue_start_point_cart);
}
else {
if(strcasecmp(xml_data->attribute_value,"log")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_segue_start_point_log);
}
}
}
}
if(strcasecmp(el,"segueEndPoint")==0) {
if(strcasecmp(xml_data->attribute,"src")==0) {
if(strcasecmp(xml_data->attribute_value,"cart")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_segue_end_point_cart);
}
else {
if(strcasecmp(xml_data->attribute_value,"log")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_segue_end_point_log);
}
}
}
}
if(strcasecmp(el,"segueGain")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_segue_gain);
}
if(strcasecmp(el,"fadeupPoint")==0) {
if(strcasecmp(xml_data->attribute,"src")==0) {
if(strcasecmp(xml_data->attribute_value,"cart")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_fadeup_point_cart);
}
else {
if(strcasecmp(xml_data->attribute_value,"log")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_fadeup_point_log);
}
}
}
}
if(strcasecmp(el,"fadeupGain")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_fadeup_gain);
}
if(strcasecmp(el,"fadedownPoint")==0) {
if(strcasecmp(xml_data->attribute,"src")==0) {
if(strcasecmp(xml_data->attribute_value,"cart")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_fadedown_point_cart);
}
else {
if(strcasecmp(xml_data->attribute_value,"log")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_fadedown_point_log);
}
}
}
}
if(strcasecmp(el,"fadedownGain")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_fadedown_gain);
}
if(strcasecmp(el,"duckUpGain")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_duckup_gain);
}
if(strcasecmp(el,"duckDownGain")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_duckdown_gain);
}
if(strcasecmp(el,"talkStartPoint")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_talk_start_point);
}
if(strcasecmp(el,"talkEndPoint")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_talk_end_point);
}
if(strcasecmp(el,"hookMode")==0) {
logline->logline_hook_mode=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"hookStartPoint")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_hook_start_point);
}
if(strcasecmp(el,"hookEndPoint")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_hook_end_point);
}
if(strcasecmp(el,"eventLength")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_event_length);
}
if(strcasecmp(el,"linkEventName")==0) {
strlcpy(logline->logline_link_event_name,xml_data->strbuf,64);
}
if(strcasecmp(el,"linkStartTime")==0) {
logline->logline_link_starttime=RD_Cnv_TString_to_msec(xml_data->strbuf);
}
if(strcasecmp(el,"linkStartSlop")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_link_start_slop);
}
if(strcasecmp(el,"linkEndSlop")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_link_end_slop);
}
if(strcasecmp(el,"linkId")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_link_id);
}
if(strcasecmp(el,"linkEmbedded")==0) {
if(strcasecmp(xml_data->strbuf,"true")==0) {
logline->logline_link_embedded=1;
}
else {
logline->logline_link_embedded=0;
}
}
if(strcasecmp(el,"extStartTime")==0) {
logline->logline_ext_starttime=RD_Cnv_TString_to_msec(xml_data->strbuf);
}
if(strcasecmp(el,"extLength")==0) {
sscanf(xml_data->strbuf,"%d",&logline->logline_ext_length);
}
if(strcasecmp(el,"extCartName")==0) {
strlcpy(logline->logline_ext_cart_name,xml_data->strbuf,32);
}
if(strcasecmp(el,"extData")==0) {
strlcpy(logline->logline_ext_data,xml_data->strbuf,32);
}
if(strcasecmp(el,"extEventId")==0) {
strlcpy(logline->logline_ext_event_id,xml_data->strbuf,32);
}
if(strcasecmp(el,"extAnncType")==0) {
strlcpy(logline->logline_ext_annc_type,xml_data->strbuf,8);
}
}
size_t __ListLogCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_ListLog(struct rd_logline *logline[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char logname[],
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
char real_logname[64];
char *real_index = &real_logname[0];
long response_code;
int i;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* Set number of recs so if fail already set */
*numrecs = 0;
if (strlen(logname)==0) {
return 400; /* Log Name Missing */
}
/* make the actual log name */
if (strlen(logname)>60) {
return 404; /* Log Name Incorrect */
}
memset(real_logname,'\0',sizeof(real_logname));
for (i = 0; i<strlen(logname);i++) {
if (logname[i]>32) {
strncpy(real_index,&logname[i],1);
real_index++;
}
}
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__ListLogElementStart,
__ListLogElementEnd);
XML_SetCharacterDataHandler(parser,__ListLogElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=22&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&NAME=%s",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
curl_easy_escape(curl,real_logname,0));
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__ListLogCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
*logline=xml_data.logline;
*numrecs = xml_data.logline_quan;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_listlog Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,112 @@
/* rd_listlog.h
*
* Header for the ListCarts Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_LISTLOG_H
#define RD_LISTLOG_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
struct rd_logline {
int logline_line;
int logline_id;
int logline_type;
int logline_cart_type;
unsigned logline_cart_number;
int logline_cut_number;
char logline_group_name[11];
char logline_group_color[10];
char logline_title[256];
char logline_artist[256];
char logline_album[256];
int logline_year;
char logline_label[65];
char logline_client[65];
char logline_agency[65];
char logline_publisher[65];
char logline_composer[65];
char logline_conductor[65];
char logline_user_defined[256];
int logline_usage_code;
int logline_enforce_length;
// char logline_forced_length[10];
int logline_forced_length;
int logline_evergreen;
int logline_source;
int logline_time_type;
int logline_starttime;
int logline_transition_type;
int logline_cut_quantity;
int logline_last_cut_played;
char logline_marker_comment[256];
char logline_marker_label[65];
char logline_origin_user[256];
struct tm logline_origin_datetime;
int logline_start_point_cart;
int logline_start_point_log;
int logline_end_point_cart;
int logline_end_point_log;
int logline_segue_start_point_cart;
int logline_segue_start_point_log;
int logline_segue_end_point_cart;
int logline_segue_end_point_log;
int logline_segue_gain;
int logline_fadeup_point_cart;
int logline_fadeup_point_log;
int logline_fadeup_gain;
int logline_fadedown_point_cart;
int logline_fadedown_point_log;
int logline_fadedown_gain;
int logline_duckup_gain;
int logline_duckdown_gain;
int logline_talk_start_point;
int logline_talk_end_point;
int logline_hook_mode;
int logline_hook_start_point;
int logline_hook_end_point;
int logline_event_length;
char logline_link_event_name[65];
int logline_link_starttime;
int logline_link_start_slop;
int logline_link_end_slop;
int logline_link_id;
int logline_link_embedded;
int logline_ext_starttime;
int logline_ext_length;
char logline_ext_cart_name[33];
char logline_ext_data[33];
char logline_ext_event_id[33];
char logline_ext_annc_type[9];
};
int RD_ListLog(struct rd_logline *logline[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char logname[],
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_LISTLOG_H

View File

@@ -0,0 +1,272 @@
/* rd_listlogs.c
*
* Implementation of the ListLogs Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_common.h"
#include "rd_getuseragent.h"
#include "rd_listlogs.h"
struct xml_data {
unsigned logs_quan;
char elem_name[256];
char strbuf[1024];
struct rd_log *logs;
};
static void XMLCALL __ListLogsElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"log")==0) { // Allocate a new log entry
xml_data->logs=realloc(xml_data->logs,
(xml_data->logs_quan+1)*sizeof(struct rd_log));
(xml_data->logs_quan)++;
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __ListLogsElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __ListLogsElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_log *logs=xml_data->logs+(xml_data->logs_quan-1);
char hold_datetime[25];
if(strcasecmp(el,"name")==0) {
strlcpy(logs->log_name,xml_data->strbuf,64);
}
if(strcasecmp(el,"serviceName")==0) {
strlcpy(logs->log_service,xml_data->strbuf,10);
}
if(strcasecmp(el,"description")==0) {
strlcpy(logs->log_description,xml_data->strbuf,64);
}
if(strcasecmp(el,"originUserName")==0) {
strlcpy(logs->log_origin_username,xml_data->strbuf,255);
}
if(strcasecmp(el,"originDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
logs->log_origin_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"purgeDate")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
logs->log_purge_date = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"linkDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
logs->log_link_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"modifiedDatetime")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
logs->log_modified_datetime = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"autoRefresh")==0) {
logs->log_autorefresh=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"startDate")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
logs->log_startdate = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"endDate")==0) {
strlcpy(hold_datetime,xml_data->strbuf,26);
logs->log_enddate = RD_Cnv_DTString_to_tm(hold_datetime);
}
if(strcasecmp(el,"scheduledTracks")==0) {
sscanf(xml_data->strbuf,"%d",&logs->log_scheduled_tracks);
}
if(strcasecmp(el,"completedTracks")==0) {
sscanf(xml_data->strbuf,"%d",&logs->log_completed_tracks);
}
if(strcasecmp(el,"musicLinks")==0) {
sscanf(xml_data->strbuf,"%d",&logs->log_music_links);
}
if(strcasecmp(el,"musicLinked")==0) {
logs->log_music_linked=RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"trafficLinks")==0) {
sscanf(xml_data->strbuf,"%d",&logs->log_traffic_links);
}
if(strcasecmp(el,"trafficLinked")==0) {
logs->log_traffic_linked=RD_ReadBool(xml_data->strbuf);
}
}
size_t __ListLogsCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_ListLogs(struct rd_log *logs[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char servicename[],
const char logname[],
const int trackable,
const char filter[],
const int recent,
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
char checked_service[11]={0};
char *check_svc = &checked_service[0];
char checked_logname[65]={0};
char *check_logname = &checked_logname[0];
int checked_trackable = 0;
int checked_recent = 0;
struct xml_data xml_data;
long response_code;
int i;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* Set number of recs so if fail already set */
*numrecs = 0;
if (trackable == 1) {
checked_trackable = 1;
}
if (recent == 1) {
checked_recent = 1;
}
memset(checked_service,'\0',sizeof(checked_service));
if ((strlen(servicename) > 0) &&
(strlen(servicename) < 11)) {
for (i = 0; i<strlen(servicename);i++) {
if (servicename[i]>32) {
strncpy(check_svc,&servicename[i],1);
check_svc++;
}
}
}
if ((strlen(logname) > 0) &&
(strlen(logname) < 65)) {
for (i = 0; i<strlen(logname);i++) {
if (logname[i]>32) {
strncpy(check_logname,&logname[i],1);
check_logname++;
}
}
}
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__ListLogsElementStart,
__ListLogsElementEnd);
XML_SetCharacterDataHandler(parser,__ListLogsElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=20&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&SERVICE_NAME=%s&LOG_NAME=%s&TRACKABLE=%d&FILTER=%s&RECENT=%d",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
curl_easy_escape(curl,checked_service,0),
curl_easy_escape(curl,checked_logname,0),
checked_trackable,
curl_easy_escape(curl,filter,0),
checked_recent);
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__ListLogsCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
*logs=xml_data.logs;
*numrecs = xml_data.logs_quan;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_listlogs Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,64 @@
/* rd_listlogs.h
*
* Header for the ListLogs Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_LISTLOGS_H
#define RD_LISTLOGS_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
struct rd_log {
char log_name[65];
char log_service[11];
char log_description[65];
char log_origin_username[256];
struct tm log_origin_datetime;
struct tm log_purge_date;
struct tm log_link_datetime;
struct tm log_modified_datetime;
int log_autorefresh;
struct tm log_startdate;
struct tm log_enddate;
int log_scheduled_tracks;
int log_completed_tracks;
int log_music_links;
int log_music_linked;
int log_traffic_links;
int log_traffic_linked;
};
int RD_ListLogs(struct rd_log *logs[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char servicename[],
const char logname[],
const int trackable,
const char filter[],
const int recent,
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_LISTLOGS_H

View File

@@ -0,0 +1,176 @@
/* rd_listschedulcodes.c
*
* Implementation of the ListSchedulCodes Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_listschedcodes.h"
#include "rd_common.h"
#include "rd_getuseragent.h"
struct xml_data {
unsigned schedcodes_quan;
char elem_name[256];
char strbuf[1024];
struct rd_schedcodes *schedcodes;
};
static void XMLCALL __ListSchedCodesElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"schedCode")==0) { // Allocate a new schedule code entry
xml_data->schedcodes=realloc(xml_data->schedcodes,
(xml_data->schedcodes_quan+1)*sizeof(struct rd_schedcodes));
(xml_data->schedcodes_quan)++;
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __ListSchedCodesElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __ListSchedCodesElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_schedcodes *schedcodes=xml_data->schedcodes+(xml_data->schedcodes_quan-1);
if(strcasecmp(el,"code")==0) {
strlcpy(schedcodes->code,xml_data->strbuf,10);
}
if(strcasecmp(el,"description")==0){
strlcpy(schedcodes->description,xml_data->strbuf,256);
}
}
size_t __ListSchedCodesCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_ListSchedCodes(struct rd_schedcodes *scodes[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* Set number of recs so if fail already set */
*numrecs = 0;
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__ListSchedCodesElementStart,
__ListSchedCodesElementEnd);
XML_SetCharacterDataHandler(parser,__ListSchedCodesElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=24&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0));
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__ListSchedCodesCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
*scodes=xml_data.schedcodes;
*numrecs = xml_data.schedcodes_quan;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_listschedcodes Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,41 @@
/* rd_listschedcodes.h
*
* Header for the ListSchedulCodes Web Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_LISTSCHEDCODES_H
#define RD_LISTSCHEDCODES_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
#include <rivwebcapi/rd_schedcodes.h>
int RD_ListSchedCodes(struct rd_schedcodes *schedcodes[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_LISTSCHEDCODES_H

View File

@@ -0,0 +1,179 @@
/* rd_listservices.c
*
* Implementation of the List Services Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_listservices.h"
#include "rd_getuseragent.h"
#include "rd_common.h"
struct xml_data {
unsigned services_quan;
char elem_name[256];
char strbuf[1024];
struct rd_service *services;
};
static void XMLCALL __ListServicesElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"service")==0) { // Allocate a new cart entry
xml_data->services=realloc(xml_data->services,
(xml_data->services_quan+1)*sizeof(struct rd_service));
(xml_data->services_quan)++;
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __ListServicesElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __ListServicesElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_service *services=xml_data->services+(xml_data->services_quan-1);
if(strcasecmp(el,"name")==0) {
strlcpy(services->service_name,xml_data->strbuf,11);
}
if(strcasecmp(el,"description")==0) {
strlcpy(services->service_description,xml_data->strbuf,256);
}
}
size_t __ListServicesCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_ListServices(struct rd_service *services[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const int trackable,
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* Set number of recs so if fail already set */
*numrecs = 0;
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__ListServicesElementStart,
__ListServicesElementEnd);
XML_SetCharacterDataHandler(parser,__ListServicesElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=21&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&TRACKABLE=%d",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
trackable);
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__ListServicesCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
*services=xml_data.services;
*numrecs = xml_data.services_quan;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_listservices Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,45 @@
/* rd_listservices.h
*
* Header for the ListCarts Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_LISTSERVICES_H
#define RD_LISTSERVICES_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
struct rd_service {
char service_name [11];
char service_description[256];
};
int RD_ListServices(struct rd_service *services[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const int trackable,
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_LISTSERVICES_H

View File

@@ -0,0 +1,184 @@
/* rd_listsystemsettings.c
*
* Implementation of the List System Settings Rivendell Access Library
*
* (C) Copyright 2017 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_listsystemsettings.h"
#include "rd_common.h"
#include "rd_getuseragent.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
struct rd_system_settings *system_settings;
};
static void XMLCALL __ListSystemSettingsElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"systemSettings")==0) { // Allocate a new systemSettings entry
xml_data->system_settings=realloc(xml_data->system_settings,
sizeof(struct rd_system_settings));
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __ListSystemSettingsElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __ListSystemSettingsElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_system_settings *system_settings=xml_data->system_settings;
if(strcasecmp(el,"sampleRate")==0) {
sscanf(xml_data->strbuf,"%u",&system_settings->sample_rate);
}
if(strcasecmp(el,"duplicateTitles")==0){
system_settings->dup_cart_titles = RD_ReadBool(xml_data->strbuf);
}
if(strcasecmp(el,"maxPostLength")==0) {
sscanf(xml_data->strbuf,"%u",&system_settings->max_post_length);
}
if(strcasecmp(el,"isciXreferencePath")==0){
strlcpy(system_settings->isci_xreference_path,xml_data->strbuf,256);
}
if(strcasecmp(el,"tempCartGroup")==0){
strlcpy(system_settings->temp_cart_group,xml_data->strbuf,11);
}
}
size_t __ListSystemSettingsCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_ListSystemSettings(struct rd_system_settings *system_settings[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* Set number of recs so if fail already set */
*numrecs = 0;
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__ListSystemSettingsElementStart,
__ListSystemSettingsElementEnd);
XML_SetCharacterDataHandler(parser,__ListSystemSettingsElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=33&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0));
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__ListSystemSettingsCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
*system_settings=xml_data.system_settings;
*numrecs = 1;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_listsystemsettings Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,47 @@
/* rd_listsystemsettings.h
*
* Header for the List System Settings Rivendell Access Library
*
* (C) Copyright 2017 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_LISTSYSTEMSETTINGS_H
#define RD_LISTSYSTEMSETTINGS_H
struct rd_system_settings {
unsigned sample_rate;
int dup_cart_titles;
unsigned max_post_length;
char isci_xreference_path[256];
char temp_cart_group[11];
};
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
int RD_ListSystemSettings(struct rd_system_settings *system_settings[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_LISTSYSTEMSETTINGS_H

View File

@@ -0,0 +1,154 @@
/* rd_removecart.c
*
* Implementation of the Remove Cart Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_removecart.h"
#include "rd_common.h"
#include "rd_getuseragent.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
};
static void XMLCALL __RemoveCartElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __RemoveCartElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __RemoveCartElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
}
size_t __RemoveCartCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_RemoveCart( const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnumber,
const char user_agent[])
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__RemoveCartElementStart,
__RemoveCartElementEnd);
XML_SetCharacterDataHandler(parser,__RemoveCartElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=13&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&CART_NUMBER=%u",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
cartnumber);
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__RemoveCartCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) { //Success
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_remocecart Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,38 @@
/* rd_removecart.h
*
* Header for the Remove Cart Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_REMOVECART_H
#define RD_REMOVECART_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
int RD_RemoveCart(const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnumber,
const char user_agent[]);
_MYRIVLIB_FINI_DECL
#endif // RD_REMOVECART_H

View File

@@ -0,0 +1,156 @@
/* rd_removecut.c
*
* Implementation of the Remove Cut Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_removecut.h"
#include "rd_common.h"
#include "rd_getuseragent.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
};
static void XMLCALL __RemoveCutElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __RemoveCutElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __RemoveCutElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
}
size_t __RemoveCutCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_RemoveCut( const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnumber,
const unsigned cutnumber,
const char user_agent[])
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__RemoveCutElementStart,
__RemoveCutElementEnd);
XML_SetCharacterDataHandler(parser,__RemoveCutElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=11&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&CART_NUMBER=%u&CUT_NUMBER=%u",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
cartnumber,
cutnumber);
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__RemoveCutCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) { //Success
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_removecut Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,39 @@
/* rd_removecut.h
*
* Header for the Remove Cut Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_REMOVECUT_H
#define RD_REMOVECUT_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
int RD_RemoveCut(const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnumber,
const unsigned cutnumber,
const char user_agent[]);
_MYRIVLIB_FINI_DECL
#endif // RD_REMOVECUT_H

View File

@@ -0,0 +1,299 @@
/* rd_savelog.c
*
* Header for the Save Log Rivendell Access Library
*
* (C) Copyright 2017 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <curl/curl.h>
#include "rd_savelog.h"
#include "rd_getuseragent.h"
char *AppendString(char *str,const char *added_str)
{
str=realloc(str,strlen(str)+strlen(added_str)+1);
strcat(str,added_str);
return str;
}
int RD_SaveLog(struct save_loghdr_values *hdrvals,
struct save_logline_values *linevals,
unsigned linevals_quan,
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char logname[],
const char user_agent[])
{
char url[1500];
char str[1024];
char dtstr[256];
char *post=malloc(1);
CURL *curl=NULL;
CURLcode res;
char errbuf[CURL_ERROR_SIZE];
long response_code;
unsigned i=0;
post[0]=0;
char user_agent_string[255];
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
//
// Log Header
//
post=AppendString(post,"COMMAND=28&");
snprintf(str,1024,"LOGIN_NAME=%s&",curl_easy_escape(curl,username,0));
post=AppendString(post,str);
snprintf(str,1024,"PASSWORD=%s&",curl_easy_escape(curl,passwd,0));
post=AppendString(post,str);
snprintf(str,1024,"TICKET=%s&",curl_easy_escape(curl,ticket,0));
post=AppendString(post,str);
snprintf(str,1024,"LOG_NAME=%s&",curl_easy_escape(curl,logname,0));
post=AppendString(post,str);
snprintf(str,1024,"SERVICE_NAME=%s&",curl_easy_escape(curl,hdrvals->loghdr_service,0));
post=AppendString(post,str);
snprintf(str,1024,"DESCRIPTION=%s&",curl_easy_escape(curl,hdrvals->loghdr_description,0));
post=AppendString(post,str);
snprintf(str,1024,"AUTO_REFRESH=%d&",hdrvals->loghdr_autorefresh);
post=AppendString(post,str);
RD_Cnv_tm_to_DTString(&hdrvals->loghdr_purge_date,dtstr);
snprintf(str,1024,"PURGE_DATE=%s&",dtstr);
post=AppendString(post,str);
RD_Cnv_tm_to_DTString(&hdrvals->loghdr_start_date,dtstr);
snprintf(str,1024,"START_DATE=%s&",dtstr);
post=AppendString(post,str);
RD_Cnv_tm_to_DTString(&hdrvals->loghdr_end_date,dtstr);
snprintf(str,1024,"END_DATE=%s&",dtstr);
post=AppendString(post,str);
snprintf(str,1024,"LINE_QUANTITY=%d",linevals_quan);
post=AppendString(post,str);
//
// Log Lines
//
for(i=0;i<linevals_quan;i++) {
snprintf(str,1024,"&LINE%u_ID=%u",i,linevals[i].logline_id);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_TYPE=%u",i,linevals[i].logline_type);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_CART_NUMBER=%u",i,
linevals[i].logline_cart_number);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_START_TIME=%u",i,linevals[i].logline_starttime);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_GRACE_TIME=%u",i,linevals[i].logline_gracetime);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_TIME_TYPE=%u",i,linevals[i].logline_time_type);
post=AppendString(post,str);
switch(linevals[i].logline_transition_type) {
case 0:
snprintf(str,1024,"&LINE%u_TRANS_TYPE=PLAY",i);
break;
case 1:
snprintf(str,1024,"&LINE%u_TRANS_TYPE=SEGUE",i);
break;
case 2:
snprintf(str,1024,"&LINE%u_TRANS_TYPE=STOP",i);
break;
}
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_START_POINT=%d",i,
linevals[i].logline_start_point_log);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_END_POINT=%d",i,
linevals[i].logline_end_point_log);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_SEGUE_START_POINT=%d",i,
linevals[i].logline_segue_start_point_log);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_SEGUE_END_POINT=%d",i,
linevals[i].logline_segue_end_point_log);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_FADEUP_POINT=%d",i,
linevals[i].logline_fadeup_point_log);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_FADEUP_GAIN=%d",i,
linevals[i].logline_fadeup_gain);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_FADEDOWN_POINT=%d",i,
linevals[i].logline_fadedown_point_log);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_FADEDOWN_GAIN=%d",i,
linevals[i].logline_fadedown_gain);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_DUCK_UP_GAIN=%d",i,
linevals[i].logline_duckup_gain);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_DUCK_DOWN_GAIN=%d",i,
linevals[i].logline_duckdown_gain);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_COMMENT=%s",i,
curl_easy_escape(curl,linevals[i].logline_marker_comment,0));
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_LABEL=%s",i,
curl_easy_escape(curl,linevals[i].logline_marker_label,0));
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_ORIGIN_USER=%s",i,
curl_easy_escape(curl,linevals[i].logline_origin_user,0));
post=AppendString(post,str);
RD_Cnv_tm_to_DTString(&linevals[i].logline_origin_datetime,dtstr);
snprintf(str,1024,"&LINE%u_ORIGIN_DATETIME=%s",i,dtstr);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_ORIGIN_USER=%s",i,
curl_easy_escape(curl,linevals[i].logline_origin_user,0));
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_EVENT_LENGTH=%u",i,
linevals[i].logline_event_length);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_LINK_EVENT_NAME=%s",i,
curl_easy_escape(curl,linevals[i].logline_link_event_name,0));
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_LINK_LENGTH=%u",i,
linevals[i].logline_link_length);
post=AppendString(post,str);
RD_Cnv_tm_to_DTString(&linevals[i].logline_link_starttime,dtstr);
snprintf(str,1024,"&LINE%u_LINK_START_TIME=%s",i,dtstr);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_LINK_START_SLOP=%u",i,
linevals[i].logline_link_start_slop);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_LINK_END_SLOP=%u",i,
linevals[i].logline_link_end_slop);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_LINK_ID=%u",i,
linevals[i].logline_link_id);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_LINK_EMBEDDED=%u",i,
linevals[i].logline_link_embedded);
post=AppendString(post,str);
RD_Cnv_tm_to_DTString(&linevals[i].logline_ext_starttime,dtstr);
snprintf(str,1024,"&LINE%u_EXT_START_TIME=%s",i,dtstr);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_EXT_LENGTH=%u",i,
linevals[i].logline_ext_length);
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_EXT_CART_NAME=%s",i,
curl_easy_escape(curl,linevals[i].logline_ext_cart_name,0));
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_EXT_DATA=%s",i,
curl_easy_escape(curl,linevals[i].logline_ext_data,0));
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_EXT_EVENT_ID=%s",i,
curl_easy_escape(curl,linevals[i].logline_ext_event_id,0));
post=AppendString(post,str);
snprintf(str,1024,"&LINE%u_EXT_ANNC_TYPE=%s",i,
curl_easy_escape(curl,linevals[i].logline_ext_annc_type,0));
post=AppendString(post,str);
}
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// curl_easy_setopt(curl,CURLOPT_VERBOSE,1);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) { //Success
return 0;
}
return (int)response_code;
}

View File

@@ -0,0 +1,89 @@
/* rd_savelog.h
*
* Header for the Save Log Rivendell Access Library
*
* (C) Copyright 2017 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_SAVELOG_H
#define RD_SAVELOG_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
struct save_loghdr_values {
char loghdr_service[11];
char loghdr_description[65];
int loghdr_autorefresh;
struct tm loghdr_purge_date;
struct tm loghdr_start_date;
struct tm loghdr_end_date;
};
struct save_logline_values {
int logline_id;
int logline_type;
int logline_source;
unsigned logline_cart_number;
int logline_starttime;
int logline_gracetime;
int logline_time_type;
int logline_transition_type;
int logline_start_point_log;
int logline_end_point_log;
int logline_segue_start_point_log;
int logline_segue_end_point_log;
int logline_fadeup_point_log;
int logline_fadeup_gain;
int logline_fadedown_point_log;
int logline_fadedown_gain;
int logline_duckup_gain;
int logline_duckdown_gain;
char logline_marker_comment[256];
char logline_marker_label[65];
char logline_origin_user[256];
struct tm logline_origin_datetime;
int logline_event_length;
char logline_link_event_name[65];
struct tm logline_link_starttime;
int logline_link_length;
int logline_link_start_slop;
int logline_link_end_slop;
int logline_link_id;
int logline_link_embedded;
struct tm logline_ext_starttime;
int logline_ext_length;
char logline_ext_cart_name[33];
char logline_ext_data[33];
char logline_ext_event_id[33];
char logline_ext_annc_type[9];
};
int RD_SaveLog(struct save_loghdr_values *hdrvals,
struct save_logline_values *linevals,
unsigned linevals_quan,
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const char logname[],
const char user_agent[]);
_MYRIVLIB_FINI_DECL
#endif // RD_SAVELOG_H

View File

@@ -0,0 +1,25 @@
/* rd_schedcodes.h
*
* Header for the RDSCHEDCODES Structure Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
*
*/
#ifndef RD_SCHEDCODES_H
#define RD_SCHEDCODES_H
struct rd_schedcodes {
char code[11];
char description[255];
};
#endif //RD_SCHEDCODES_H

View File

@@ -0,0 +1,189 @@
/* rd_trimaudio.c
*
* Implementation of the TrimAudio Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_trimaudio.h"
#include "rd_getuseragent.h"
#include "rd_common.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
struct rd_trimaudio *trimaudio;
};
static void XMLCALL __TrimAudioElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
if(strcasecmp(el,"trimPoint")==0) { // Allocate a new trimaudio entry
xml_data->trimaudio=realloc(xml_data->trimaudio,
sizeof(struct rd_trimaudio));
}
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __TrimAudioElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __TrimAudioElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
struct rd_trimaudio *trimaudio=xml_data->trimaudio;
if(strcasecmp(el,"cartNumber")==0) {
sscanf(xml_data->strbuf,"%u",&trimaudio->cart_number);
}
if(strcasecmp(el,"cutNumber")==0){
sscanf(xml_data->strbuf,"%u",&trimaudio->cut_number);
}
if(strcasecmp(el,"trimLevel")==0) {
sscanf(xml_data->strbuf,"%d",&trimaudio->trimlevel);
}
if(strcasecmp(el,"startTrimPoint")==0){
sscanf(xml_data->strbuf,"%d",&trimaudio->starttrimpoint);
}
if(strcasecmp(el,"endTrimPoint")==0){
sscanf(xml_data->strbuf,"%d",&trimaudio->endtrimpoint);
}
}
size_t __TrimAudioCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_TrimAudio(struct rd_trimaudio *trimaudio[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnumber,
const unsigned cutnumber,
const int trimlevel,
const char user_agent[],
unsigned *numrecs)
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/* Set number of recs so if fail already set */
*numrecs = 0;
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__TrimAudioElementStart,
__TrimAudioElementEnd);
XML_SetCharacterDataHandler(parser,__TrimAudioElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=17&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&CART_NUMBER=%u&CUT_NUMBER=%u&TRIM_LEVEL=%d",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
cartnumber,
cutnumber,
trimlevel);
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__TrimAudioCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
*trimaudio=xml_data.trimaudio;
*numrecs = 1;
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_trimaudio Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,50 @@
/* rd_trimaudio.h
*
* Header for the Trim Audio Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_TRIMAUDIO_H
#define RD_TRIMAUDIO_H
struct rd_trimaudio {
unsigned cart_number;
unsigned cut_number;
int trimlevel;
int starttrimpoint;
int endtrimpoint;
};
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
int RD_TrimAudio(struct rd_trimaudio *trimaudio[],
const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnumber,
const unsigned cutnumber,
const int trimlevel,
const char user_agent[],
unsigned *numrecs);
_MYRIVLIB_FINI_DECL
#endif // RD_TRIMAUDIO_H

View File

@@ -0,0 +1,176 @@
/* rd_unassignschedulcodes.c
*
* Implementation of the UnassignSchedulCode Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdlib.h>
#include <string.h>
#include <curl/curl.h>
#include <expat.h>
#include "rd_unassignschedcode.h"
#include "rd_common.h"
#include "rd_getuseragent.h"
struct xml_data {
char elem_name[256];
char strbuf[1024];
};
static void XMLCALL __UnAssignSchedCodeElementStart(void *data, const char *el,
const char **attr)
{
struct xml_data *xml_data=(struct xml_data *)data;
strlcpy(xml_data->elem_name,el,256);
memset(xml_data->strbuf,0,1024);
}
static void XMLCALL __UnAssignSchedCodeElementData(void *data,const XML_Char *s,
int len)
{
struct xml_data *xml_data=(struct xml_data *)data;
memcpy(xml_data->strbuf+strlen(xml_data->strbuf),s,len);
}
static void XMLCALL __UnAssignSchedCodeElementEnd(void *data, const char *el)
{
struct xml_data *xml_data=(struct xml_data *)data;
}
size_t __UnAssignSchedCodeCallback(void *ptr, size_t size, size_t nmemb, void *userdata)
{
XML_Parser p=(XML_Parser)userdata;
XML_Parse(p,ptr,size*nmemb,0);
return size*nmemb;
}
int RD_UnassignSchedCode( const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnum,
const char code[],
const char user_agent[])
{
char post[1500];
char url[1500];
CURL *curl=NULL;
XML_Parser parser;
struct xml_data xml_data;
long response_code;
int i;
int code_valid = 1;
char errbuf[CURL_ERROR_SIZE];
CURLcode res;
char user_agent_string[255];
/* Check Code */
for (i = 0 ; i < strlen(code) ; i++) {
if ((code[i]==32) || (i > 9)) {
code_valid=0;
break;
}
}
if (!code_valid)
{
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," Scheduler Code : %s Is Invalid! \n",code);
#endif
return -1;
}
if((curl=curl_easy_init())==NULL) {
curl_easy_cleanup(curl);
return -1;
}
/*
* Setup the CURL call
*/
memset(&xml_data,0,sizeof(xml_data));
parser=XML_ParserCreate(NULL);
XML_SetUserData(parser,&xml_data);
XML_SetElementHandler(parser,__UnAssignSchedCodeElementStart,
__UnAssignSchedCodeElementEnd);
XML_SetCharacterDataHandler(parser,__UnAssignSchedCodeElementData);
snprintf(url,1500,"http://%s/rd-bin/rdxport.cgi",hostname);
snprintf(post,1500,"COMMAND=26&LOGIN_NAME=%s&PASSWORD=%s&TICKET=%s&CART_NUMBER=%u&CODE=%s",
curl_easy_escape(curl,username,0),
curl_easy_escape(curl,passwd,0),
curl_easy_escape(curl,ticket,0),
cartnum,
curl_easy_escape(curl,code,0));
curl_easy_setopt(curl,CURLOPT_WRITEDATA,parser);
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,__UnAssignSchedCodeCallback);
curl_easy_setopt(curl,CURLOPT_URL,url);
curl_easy_setopt(curl,CURLOPT_POST,1);
curl_easy_setopt(curl,CURLOPT_POSTFIELDS,post);
curl_easy_setopt(curl,CURLOPT_NOPROGRESS,1);
curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,errbuf);
// Check if User Agent Present otherwise set to default
if (strlen(user_agent)> 0){
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent);
}
else
{
strcpy(user_agent_string, RD_GetUserAgent());
strcat(user_agent_string,VERSION);
curl_easy_setopt(curl, CURLOPT_USERAGENT,user_agent_string);
}
res = curl_easy_perform(curl);
if(res != CURLE_OK) {
#ifdef RIVC_DEBUG_OUT
size_t len = strlen(errbuf);
fprintf(stderr, "\nlibcurl error: (%d)", res);
if (len)
fprintf(stderr, "%s%s", errbuf,
((errbuf[len-1] != '\n') ? "\n" : ""));
else
fprintf(stderr, "%s\n", curl_easy_strerror(res));
#endif
curl_easy_cleanup(curl);
return -1;
}
/* The response OK - so figure out if we got what we wanted.. */
curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&response_code);
curl_easy_cleanup(curl);
if (response_code > 199 && response_code < 300) {
return 0;
}
else {
#ifdef RIVC_DEBUG_OUT
fprintf(stderr," rd_unassignschedcode Call Returned Error: %s\n",xml_data.strbuf);
#endif
return (int)response_code;
}
}

View File

@@ -0,0 +1,39 @@
/* rd_unassignschedcodes.h
*
* Header for the UnassignSchedCodes Web Rivendell Access Library
*
* (C) Copyright 2015 Todd Baker <bakert@rfa.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* 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, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef RD_UNASSIGNSCHEDCODE_H
#define RD_UNASSIGNSCHEDCODE_H
#include <rivwebcapi/rd_common.h>
_MYRIVLIB_INIT_DECL
int RD_UnassignSchedCode(const char hostname[],
const char username[],
const char passwd[],
const char ticket[],
const unsigned cartnum,
const char code[],
const char user_agent[]);
_MYRIVLIB_FINI_DECL
#endif // RD_UNASSIGNSCHEDCODE_H