2 * This program is free software; you can redistribute it and/or modify
3 * it under the terms of the GNU General Public License as published by
4 * the Free Software Foundation; either version 2 of the License, or
5 * (at your option) any later version.
7 * This program is distributed in the hope that it will be useful,
8 * but WITHOUT ANY WARRANTY; without even the implied warranty of
9 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 * GNU General Public License for more details.
12 * You should have received a copy of the GNU General Public License
13 * along with this program; if not, write to the Free Software
14 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18 * Author : Boris Mikhailenko <stg34@stargazer.dp.ua>
21 #include "settings_impl.h"
23 #include "stg/logger.h"
24 #include "stg/dotconfpp.h"
25 #include "stg/common.h"
34 struct Error : public std::runtime_error
36 Error(const std::string& message) : runtime_error(message) {}
39 std::vector<std::string> toValues(const DOTCONFDocumentNode& node)
41 std::vector<std::string> values;
44 const char* value = NULL;
45 while ((value = node.getValue(i++)) != NULL)
46 values.push_back(value);
51 std::vector<PARAM_VALUE> toPVS(const DOTCONFDocumentNode& node)
53 std::vector<PARAM_VALUE> pvs;
55 const DOTCONFDocumentNode* child = node.getChildNode();
58 if (child->getName() == NULL)
61 if (child->getChildNode() == NULL)
62 pvs.push_back(PARAM_VALUE(child->getName(), toValues(*child)));
64 pvs.push_back(PARAM_VALUE(child->getName(), toValues(*child), toPVS(*child)));
66 child = child->getNextNode();
72 unsigned toPeriod(const char* value)
75 throw Error("No detail stat period value.");
77 std::string period(value);
80 else if (period == "1/2")
82 else if (period == "1/4")
84 else if (period == "1/6")
87 throw Error("Invalid detail stat period value: '" + period + "'. Should be one of '1', '1/2', '1/4' or '1/6'.");
92 //-----------------------------------------------------------------------------
93 SETTINGS_IMPL::SETTINGS_IMPL(const std::string & cd)
94 : modulesPath("/usr/lib/stg"),
96 confDir(cd.empty() ? "/etc/stargazer" : cd),
98 rules(confDir + "/rules"),
99 logFile("/var/log/stargazer.log"),
100 pidFile("/var/run/stargazer.pid"),
101 monitorDir("/var/stargazer/monitoring"),
103 detailStatWritePeriod(dsPeriod_1_6),
111 freeMbAllowInet(false),
112 dayFeeIsLastDay(false),
113 writeFreeMbTraffCost(false),
117 reconnectOnTariffChange(false),
118 logger(GetStgLogger())
121 //-----------------------------------------------------------------------------
122 SETTINGS_IMPL::SETTINGS_IMPL(const SETTINGS_IMPL & rval)
125 modulesPath(rval.modulesPath),
126 dirName(rval.dirName),
127 confDir(rval.confDir),
128 scriptsDir(rval.scriptsDir),
130 logFile(rval.logFile),
131 pidFile(rval.pidFile),
132 monitorDir(rval.monitorDir),
133 monitoring(rval.monitoring),
134 detailStatWritePeriod(rval.detailStatWritePeriod),
135 statWritePeriod(rval.statWritePeriod),
136 stgExecMsgKey(rval.stgExecMsgKey),
137 executersNum(rval.executersNum),
138 fullFee(rval.fullFee),
140 dayResetTraff(rval.dayResetTraff),
141 spreadFee(rval.spreadFee),
142 freeMbAllowInet(rval.freeMbAllowInet),
143 dayFeeIsLastDay(rval.dayFeeIsLastDay),
144 writeFreeMbTraffCost(rval.writeFreeMbTraffCost),
145 showFeeInCash(rval.showFeeInCash),
146 messageTimeout(rval.messageTimeout),
147 feeChargeType(rval.feeChargeType),
148 reconnectOnTariffChange(rval.reconnectOnTariffChange),
149 modulesSettings(rval.modulesSettings),
150 storeModuleSettings(rval.storeModuleSettings),
151 logger(GetStgLogger())
154 //-----------------------------------------------------------------------------
155 SETTINGS_IMPL & SETTINGS_IMPL::operator=(const SETTINGS_IMPL & rhs)
157 modulesPath = rhs.modulesPath;
158 dirName = rhs.dirName;
159 confDir = rhs.confDir;
160 scriptsDir = rhs.scriptsDir;
162 logFile = rhs.logFile;
163 pidFile = rhs.pidFile;
164 monitorDir = rhs.monitorDir;
165 scriptParams = rhs.scriptParams;
166 monitoring = rhs.monitoring;
167 detailStatWritePeriod = rhs.detailStatWritePeriod;
168 statWritePeriod = rhs.statWritePeriod;
169 stgExecMsgKey = rhs.stgExecMsgKey;
170 executersNum = rhs.executersNum;
171 fullFee = rhs.fullFee;
173 dayResetTraff = rhs.dayResetTraff;
174 spreadFee = rhs.spreadFee;
175 freeMbAllowInet = rhs.freeMbAllowInet;
176 dayFeeIsLastDay = rhs.dayFeeIsLastDay;
177 writeFreeMbTraffCost = rhs.writeFreeMbTraffCost;
178 showFeeInCash = rhs.showFeeInCash;
179 messageTimeout = rhs.messageTimeout;
180 feeChargeType = rhs.feeChargeType;
181 reconnectOnTariffChange = rhs.reconnectOnTariffChange;
183 modulesSettings = rhs.modulesSettings;
184 storeModuleSettings = rhs.storeModuleSettings;
187 //-----------------------------------------------------------------------------
188 void SETTINGS_IMPL::ErrorCallback(void * data, const char * buf)
190 printfd(__FILE__, "SETTINGS_IMPL::ErrorCallback() - %s\n", buf);
191 SETTINGS_IMPL * settings = static_cast<SETTINGS_IMPL *>(data);
192 settings->logger("%s", buf);
194 //-----------------------------------------------------------------------------
195 int SETTINGS_IMPL::ReadSettings()
197 const char * requiredOptions[] = {
203 "DetailStatWritePeriod",
209 "WriteFreeMbTraffCost",
212 int storeModulesCount = 0;
213 modulesSettings.clear();
215 DOTCONFDocument conf(DOTCONFDocument::CASEINSENSITIVE);
216 conf.setErrorCallback(SETTINGS_IMPL::ErrorCallback, this);
217 conf.setRequiredOptionNames(requiredOptions);
218 std::string confFile = confDir + "/stargazer.conf";
220 if(conf.setContent(confFile.c_str()) != 0)
222 strError = "Cannot read file " + confFile;
226 const DOTCONFDocumentNode * node = conf.getFirstNode();
230 if (strcasecmp(node->getName(), "ScriptDir") == 0)
232 scriptsDir = node->getValue(0);
235 if (strcasecmp(node->getName(), "LogFile") == 0)
237 logFile = node->getValue(0);
240 if (strcasecmp(node->getName(), "PIDFile") == 0)
242 pidFile = node->getValue(0);
245 if (strcasecmp(node->getName(), "ModulesPath") == 0)
247 modulesPath = node->getValue(0);
250 if (strcasecmp(node->getName(), "Rules") == 0)
252 rules = node->getValue(0);
255 if (strcasecmp(node->getName(), "DetailStatWritePeriod") == 0)
259 detailStatWritePeriod = toPeriod(node->getValue(0));
261 catch (const Error& error)
263 strError = error.what();
268 if (strcasecmp(node->getName(), "StatWritePeriod") == 0)
270 if (ParseUnsignedInRange(node->getValue(0), 1, 1440, &statWritePeriod) != 0)
272 strError = "Incorrect StatWritePeriod value: \'" + std::string(node->getValue(0)) + "\'";
277 if (strcasecmp(node->getName(), "ExecMsgKey") == 0)
279 if (ParseInt(node->getValue(0), &stgExecMsgKey) != 0)
281 strError = "Incorrect ExecMsgKey value: \'" + std::string(node->getValue(0)) + "\'";
286 if (strcasecmp(node->getName(), "ExecutersNum") == 0)
288 if (ParseUnsignedInRange(node->getValue(0), 1, 1024, &executersNum) != 0)
290 strError = "Incorrect ExecutersNum value: \'" + std::string(node->getValue(0)) + "\'";
295 if (strcasecmp(node->getName(), "DayFee") == 0)
297 if (ParseUnsignedInRange(node->getValue(0), 0, 31, &dayFee) != 0)
299 strError = "Incorrect DayFee value: \'" + std::string(node->getValue(0)) + "\'";
304 if (strcasecmp(node->getName(), "FullFee") == 0)
306 if (ParseYesNo(node->getValue(0), &fullFee) != 0)
308 strError = "Incorrect FullFee value: \'" + std::string(node->getValue(0)) + "\'";
313 if (strcasecmp(node->getName(), "DayResetTraff") == 0)
315 if (ParseUnsignedInRange(node->getValue(0), 0, 31, &dayResetTraff) != 0)
317 strError = "Incorrect DayResetTraff value: \'" + std::string(node->getValue(0)) + "\'";
322 if (strcasecmp(node->getName(), "SpreadFee") == 0)
324 if (ParseYesNo(node->getValue(0), &spreadFee) != 0)
326 strError = "Incorrect SpreadFee value: \'" + std::string(node->getValue(0)) + "\'";
331 if (strcasecmp(node->getName(), "FreeMbAllowInet") == 0)
333 if (ParseYesNo(node->getValue(0), &freeMbAllowInet) != 0)
335 strError = "Incorrect FreeMbAllowInet value: \'" + std::string(node->getValue(0)) + "\'";
340 if (strcasecmp(node->getName(), "DayFeeIsLastDay") == 0)
342 if (ParseYesNo(node->getValue(0), &dayFeeIsLastDay) != 0)
344 strError = "Incorrect DayFeeIsLastDay value: \'" + std::string(node->getValue(0)) + "\'";
349 if (strcasecmp(node->getName(), "WriteFreeMbTraffCost") == 0)
351 if (ParseYesNo(node->getValue(0), &writeFreeMbTraffCost) != 0)
353 strError = "Incorrect WriteFreeMbTraffCost value: \'" + std::string(node->getValue(0)) + "\'";
358 if (strcasecmp(node->getName(), "ShowFeeInCash") == 0)
360 if (ParseYesNo(node->getValue(0), &showFeeInCash) != 0)
362 strError = "Incorrect ShowFeeInCash value: \'" + std::string(node->getValue(0)) + "\'";
367 if (strcasecmp(node->getName(), "MonitorDir") == 0)
369 monitorDir = node->getValue(0);
373 if (!lstat(monitorDir.c_str(), &stat) && S_ISDIR(stat.st_mode))
379 if (strcasecmp(node->getName(), "MessageTimeout") == 0)
381 if (ParseUnsigned(node->getValue(0), &messageTimeout) != 0)
383 strError = "Incorrect MessageTimeout value: \'" + std::string(node->getValue(0)) + "\'";
388 if (strcasecmp(node->getName(), "FeeChargeType") == 0)
390 if (ParseUnsignedInRange(node->getValue(0), 0, 3, &feeChargeType) != 0)
392 strError = "Incorrect FeeChargeType value: \'" + std::string(node->getValue(0)) + "\'";
397 if (strcasecmp(node->getName(), "ReconnectOnTariffChange") == 0)
399 if (ParseYesNo(node->getValue(0), &reconnectOnTariffChange) != 0)
401 strError = "Incorrect ReconnectOnTariffChange value: \'" + std::string(node->getValue(0)) + "\'";
406 if (strcasecmp(node->getName(), "DirNames") == 0)
408 const DOTCONFDocumentNode * child = node->getChildNode();
411 const DOTCONFDocumentNode * dirNameNode;
412 dirName.reserve(DIR_NUM);
413 for (int i = 0; i < DIR_NUM; i++)
416 sprintf(strDirName, "DirName%d", i);
417 dirNameNode = conf.findNode(strDirName, node);
418 if (dirNameNode && dirNameNode->getValue(0))
420 dirName[i] = dirNameNode->getValue(0);
426 if (strcasecmp(node->getName(), "StoreModule") == 0)
428 if (node->getValue(1))
430 strError = "Unexpected \'" + std::string(node->getValue(1)) + "\'.";
434 if (storeModulesCount)
436 strError = "Should be only one StoreModule.";
441 if (node->getValue(0) == NULL)
443 strError = "No module name in the StoreModule section.";
446 storeModuleSettings.moduleName = node->getValue(0);
447 storeModuleSettings.moduleParams = toPVS(*node);
450 if (strcasecmp(node->getName(), "Modules") == 0)
452 if (node->getValue(0))
454 strError = "Unexpected \'" + std::string(node->getValue(0)) + "\'.";
457 const DOTCONFDocumentNode * child = node->getChildNode();
460 if (strcasecmp(child->getName(), "Module") != 0)
462 child = child->getNextNode();
466 if (child->getValue(0) == NULL)
468 strError = "No module name in the Module section.";
472 modulesSettings.push_back(MODULE_SETTINGS(child->getValue(0), toPVS(*child)));
474 child = child->getNextNode();
478 if (strcasecmp(node->getName(), "ScriptParams") == 0)
480 for (int i = 0; node->getValue(i) != NULL; ++i)
482 scriptParams.push_back(node->getValue(i));
485 node = node->getNextNode();
490 //-----------------------------------------------------------------------------