]> git.vomp.tv Git - jsonserver.git/blob - jsonserver.c
Switch to libconfig++
[jsonserver.git] / jsonserver.c
1 /*
2  * jsonserver.c: A plugin for the Video Disk Recorder
3  *
4  * See the README file for copyright information and how to reach the author.
5  *
6  */
7
8 #include <vdr/plugin.h>
9 #include <stdio.h>
10
11 // Config docs: http://www.hyperrealm.com/libconfig/libconfig_manual.html#The-C_002b_002b-API
12 #include <libconfig.h++>
13
14 #include "mongoose.h"
15 #include "handler.h"
16 #include "log.h"
17
18 static const char *VERSION        = "0.0.1";
19 static const char *DESCRIPTION    = "JSON data server plugin for VDR";
20 static const char *MAINMENUENTRY  = "Jsonserver";
21
22 class cPluginJsonserver : public cPlugin {
23 private:
24   // Add any member variables or functions you may need here.
25   struct mg_context *mg;
26   Log* log;
27   libconfig::Config config;
28   bool mgRunning;
29 public:
30   cPluginJsonserver(void);
31   virtual ~cPluginJsonserver();
32   virtual const char *Version(void) { return VERSION; }
33   virtual const char *Description(void) { return DESCRIPTION; }
34   virtual const char *CommandLineHelp(void);
35   virtual bool ProcessArgs(int argc, char *argv[]);
36   virtual bool Initialize(void);
37   virtual bool Start(void);
38   virtual void Stop(void);
39   virtual void Housekeeping(void);
40   virtual void MainThreadHook(void);
41   virtual cString Active(void);
42   virtual time_t WakeupTime(void);
43   virtual const char *MainMenuEntry(void) { return MAINMENUENTRY; }
44   virtual cOsdObject *MainMenuAction(void);
45   virtual cMenuSetupPage *SetupMenu(void);
46   virtual bool SetupParse(const char *Name, const char *Value);
47   virtual bool Service(const char *Id, void *Data = NULL);
48   virtual const char **SVDRPHelpPages(void);
49   virtual cString SVDRPCommand(const char *Command, const char *Option, int &ReplyCode);
50   };
51
52 cPluginJsonserver::cPluginJsonserver(void)
53 {
54   // Initialize any member variables here.
55   // DON'T DO ANYTHING ELSE THAT MAY HAVE SIDE EFFECTS, REQUIRE GLOBAL
56   // VDR OBJECTS TO EXIST OR PRODUCE ANY OUTPUT!
57
58   log = NULL;
59   mgRunning = false;
60 }
61
62 cPluginJsonserver::~cPluginJsonserver()
63 {
64   // Clean up after yourself!
65   if (log) delete log;
66   log = NULL;
67 }
68
69 const char *cPluginJsonserver::CommandLineHelp(void)
70 {
71   // Return a string that describes all known command line options.
72   return NULL;
73 }
74
75 bool cPluginJsonserver::ProcessArgs(int argc, char *argv[])
76 {
77   // Implement command line argument processing here if applicable.
78   return true;
79 }
80
81 bool cPluginJsonserver::Initialize(void)
82 {
83   // Initialize any background activities the plugin shall perform.
84   return true;
85 }
86
87 bool cPluginJsonserver::Start(void)
88 {
89   // Start any background activities the plugin shall perform.
90   const char* configDir = cPlugin::ConfigDirectory("jsonserver");
91   if (!configDir)
92   {
93     dsyslog("jsonserver: Error: Could not get config dir from VDR");
94     return false;
95   }
96
97   std::string configFile(std::string(configDir) + std::string("/server.conf"));
98   dsyslog("%s", configFile.c_str());
99   try
100   {
101     config.readFile(configFile.c_str());
102   }
103   catch (const libconfig::FileIOException &fioex)
104   {
105     dsyslog("jsonserver: Failed to read config file");
106     return false;
107   }
108   catch(const libconfig::ParseException &pex)
109   {
110     dsyslog("jsonserver: Config parse error at %s: %i - %s", pex.getFile(), pex.getLine(), pex.getError());
111     return false;
112   }
113
114   std::string cfgLogFilename;
115   if (config.lookupValue("log-file", cfgLogFilename))
116   {
117     log = new Log();
118     log->init(Log::DEBUG, cfgLogFilename.c_str());
119     log->log("Main", Log::INFO, "Logging started");
120   }
121   else
122   {
123     dsyslog("jsonserver: Logging disabled");
124   }
125
126   std::string cfgDocRoot;
127   if (!config.lookupValue("doc-root", cfgDocRoot))
128   {
129     log->log("Main", Log::CRIT, "Failed to load doc-root from config");
130     dsyslog("jsonserver: Could not load JS App Dir from plugin config file");
131     delete log;
132     log = NULL;
133     return false;
134   }
135
136   std::string cfgPort;
137   if (!config.lookupValue("http-port", cfgPort))
138   {
139     log->log("Main", Log::CRIT, "Failed to load http-port from config");
140     dsyslog("jsonserver: Could not load http-port from plugin config file");
141     delete log;
142     log = NULL;
143     return false;
144   }
145
146   std::string cfgSSLFilename;
147   if (!config.lookupValue("ssl-pem-file", cfgSSLFilename))
148   {
149     log->log("Main", Log::CRIT, "Failed to load ssl-pem-file from config");
150     dsyslog("jsonserver: Could not load ssl-pem-file from plugin config file");
151     delete log;
152     log = NULL;
153     return false;
154   }
155
156   // Make Mongoose options
157   const char *options[] =
158   {
159     "document_root", cfgDocRoot.c_str(),
160     "listening_ports", cfgPort.c_str(),
161     "num_threads", "5",
162     "ssl_certificate", cfgSSLFilename.c_str(),
163     NULL
164   };
165
166   // Prepare callbacks structure. We have only one callback, the rest are NULL.
167   struct mg_callbacks callbacks;
168   memset(&callbacks, 0, sizeof(callbacks));
169   callbacks.begin_request = jsonserver_request_handler;
170   
171   mg = mg_start(&callbacks, NULL, options);
172   log->log("JSONServer", Log::INFO, "Mongoose started");
173   mgRunning = true;
174   return true;
175 }
176
177 void cPluginJsonserver::Stop(void)
178 {
179   // Stop any background activities the plugin is performing.
180   if (mgRunning) mg_stop(mg);
181   mgRunning = false;
182 }
183
184 void cPluginJsonserver::Housekeeping(void)
185 {
186   // Perform any cleanup or other regular tasks.
187 }
188
189 void cPluginJsonserver::MainThreadHook(void)
190 {
191   // Perform actions in the context of the main program thread.
192   // WARNING: Use with great care - see PLUGINS.html!
193 }
194
195 cString cPluginJsonserver::Active(void)
196 {
197   // Return a message string if shutdown should be postponed
198   return NULL;
199 }
200
201 time_t cPluginJsonserver::WakeupTime(void)
202 {
203   // Return custom wakeup time for shutdown script
204   return 0;
205 }
206
207 cOsdObject *cPluginJsonserver::MainMenuAction(void)
208 {
209   // Perform the action when selected from the main VDR menu.
210   return NULL;
211 }
212
213 cMenuSetupPage *cPluginJsonserver::SetupMenu(void)
214 {
215   // Return a setup menu in case the plugin supports one.
216   return NULL;
217 }
218
219 bool cPluginJsonserver::SetupParse(const char *Name, const char *Value)
220 {
221   // Parse your own setup parameters and store their values.
222   return false;
223 }
224
225 bool cPluginJsonserver::Service(const char *Id, void *Data)
226 {
227   // Handle custom service requests from other plugins
228   return false;
229 }
230
231 const char **cPluginJsonserver::SVDRPHelpPages(void)
232 {
233   // Return help text for SVDRP commands this plugin implements
234   return NULL;
235 }
236
237 cString cPluginJsonserver::SVDRPCommand(const char *Command, const char *Option, int &ReplyCode)
238 {
239   // Process SVDRP commands this plugin implements
240   return NULL;
241 }
242
243 VDRPLUGINCREATOR(cPluginJsonserver); // Don't touch this!