]> git.stg.codes - stg.git/blob - projects/stargazer/plugins/configuration/sgconfig/parser_tariff.cpp
Optimized sending answers in sgconfig.
[stg.git] / projects / stargazer / plugins / configuration / sgconfig / parser_tariff.cpp
1 #include <cstdio> // snprintf
2 #include <cstring>
3
4 #include "stg/tariffs.h"
5 #include "parser.h"
6
7 const int pt_mega = 1024 * 1024;
8 //-----------------------------------------------------------------------------
9 //  GET TARIFFS
10 //-----------------------------------------------------------------------------
11 int PARSER_GET_TARIFFS::ParseStart(void *, const char * el, const char **)
12 {
13 if (strcasecmp(el, "GetTariffs") == 0)
14     {
15     return 0;
16     }
17 return -1;
18 }
19 //-----------------------------------------------------------------------------
20 int PARSER_GET_TARIFFS::ParseEnd(void *, const char * el)
21 {
22 if (strcasecmp(el, "GetTariffs") == 0)
23     {
24     CreateAnswer();
25     return 0;
26     }
27 return -1;
28 }
29 //-----------------------------------------------------------------------------
30 void PARSER_GET_TARIFFS::CreateAnswer()
31 {
32 answer = "<Tariffs>";
33
34 std::list<TARIFF_DATA> dataList;
35 tariffs->GetTariffsData(&dataList);
36 std::list<TARIFF_DATA>::const_iterator it = dataList.begin();
37 for (; it != dataList.end(); ++it)
38     {
39     answer += "<tariff name=\"" + it->tariffConf.name + "\">";
40
41     for (size_t i = 0; i < DIR_NUM; i++)
42         answer += "<Time" + x2str(i) + " value=\"" +
43             x2str(it->dirPrice[i].hDay)   + ":" + x2str(it->dirPrice[i].mDay)   + "-" +
44             x2str(it->dirPrice[i].hNight) + ":" + x2str(it->dirPrice[i].mNight) + "\"/>";
45
46     answer += "<PriceDayA value=\"";
47     bool first = true;
48     for (size_t i = 0; i < DIR_NUM; i++)
49         {
50         if (first)
51             first = false;
52         else
53             answer += "/";
54         answer += x2str(it->dirPrice[i].priceDayA * pt_mega);
55         }
56     answer += "\"/>";
57
58     answer += "<PriceDayB value=\"";
59     first = true;
60     for (size_t i = 0; i < DIR_NUM; i++)
61         {
62         if (first)
63             first = false;
64         else
65             answer += "/";
66         answer += x2str(it->dirPrice[i].priceDayB * pt_mega);
67         }
68     answer += "\"/>";
69
70     answer += "<PriceNightA value=\"";
71     first = true;
72     for (size_t i = 0; i < DIR_NUM; i++)
73         {
74         if (first)
75             first = false;
76         else
77             answer += "/";
78         answer += x2str(it->dirPrice[i].priceNightA * pt_mega);
79         }
80     answer += "\"/>";
81
82     answer += "<PriceNightB value=\"";
83     first = true;
84     for (size_t i = 0; i < DIR_NUM; i++)
85         {
86         if (first)
87             first = false;
88         else
89             answer += "/";
90         answer += x2str(it->dirPrice[i].priceNightB * pt_mega);
91         }
92     answer += "\"/>";
93
94     answer += "<Threshold value=\"";
95     first = true;
96     for (size_t i = 0; i < DIR_NUM; i++)
97         {
98         if (first)
99             first = false;
100         else
101             answer += "/";
102         answer += x2str(it->dirPrice[i].threshold);
103         }
104     answer += "\"/>";
105
106     answer += "<SinglePrice value=\"";
107     first = true;
108     for (size_t i = 0; i < DIR_NUM; i++)
109         {
110         if (first)
111             first = false;
112         else
113             answer += "/";
114         answer += (it->dirPrice[i].singlePrice ? "1" : "0");
115         }
116     answer += "\"/>";
117
118     answer += "<NoDiscount value=\"";
119     first = true;
120     for (size_t i = 0; i < DIR_NUM; i++)
121         {
122         if (first)
123             first = false;
124         else
125             answer += "/";
126         answer += (it->dirPrice[i].noDiscount ? "1" : "0");
127         }
128     answer += "\"/>";
129
130     answer += "<Fee value=\"" + x2str(it->tariffConf.fee) + "\"/>";
131
132     answer += "<PassiveCost value=\"" + x2str(it->tariffConf.passiveCost) + "\"/>";
133
134     answer += "<Free value=\"" + x2str(it->tariffConf.free) + "\"/>";
135
136     switch (it->tariffConf.traffType)
137         {
138         case TRAFF_UP:
139             answer += "<TraffType value=\"up\"/>";
140             break;
141         case TRAFF_DOWN:
142             answer += "<TraffType value=\"down\"/>";
143             break;
144         case TRAFF_UP_DOWN:
145             answer += "<TraffType value=\"up+down\"/>";
146             break;
147         case TRAFF_MAX:
148             answer += "<TraffType value=\"max\"/>";
149             break;
150         }
151
152     answer += "<Period value=\"" + TARIFF::PeriodToString(it->tariffConf.period) + "\"/>";
153
154     answer += "</tariff>";
155     }
156 answer += "</Tariffs>";
157 }
158 //-----------------------------------------------------------------------------
159 //  ADD TARIFF
160 //-----------------------------------------------------------------------------
161 int PARSER_ADD_TARIFF::ParseStart(void *, const char * el, const char ** attr)
162 {
163 if (strcasecmp(el, "AddTariff") == 0)
164     {
165     if (attr[1])
166         {
167         tariffToAdd = attr[1];
168         }
169     return 0;
170     }
171 return -1;
172 }
173 //-----------------------------------------------------------------------------
174 int PARSER_ADD_TARIFF::ParseEnd(void *, const char * el)
175 {
176 if (strcasecmp(el, "AddTariff") == 0)
177     {
178     CreateAnswer();
179     return 0;
180     }
181 return -1;
182 }
183 //-----------------------------------------------------------------------------
184 void PARSER_ADD_TARIFF::CreateAnswer()
185 {
186 if (tariffs->Add(tariffToAdd, currAdmin) == 0)
187     answer = "<AddTariff Result=\"Ok\"/>";
188 else
189     answer = "<AddTariff Result=\"Error. " + tariffs->GetStrError() + "\"/>";
190 }
191 //-----------------------------------------------------------------------------
192 //  DEL TARIFF
193 //-----------------------------------------------------------------------------
194 int PARSER_DEL_TARIFF::ParseStart(void *, const char * el, const char ** attr)
195 {
196 strError = "";
197 if (strcasecmp(el, "DelTariff") == 0)
198     {
199     tariffToDel = attr[1];
200     return 0;
201     }
202 return -1;
203 }
204 //-----------------------------------------------------------------------------
205 int PARSER_DEL_TARIFF::ParseEnd(void *, const char * el)
206 {
207 if (strcasecmp(el, "DelTariff") == 0)
208     {
209     CreateAnswer();
210     return 0;
211     }
212 return -1;
213 }
214 //-----------------------------------------------------------------------------
215 void PARSER_DEL_TARIFF::CreateAnswer()
216 {
217 if (users->TariffInUse(tariffToDel))
218     answer = "<DelTariff Result=\"Error. Tariff \'" + tariffToDel + "\' cannot be deleted. Tariff in use.\"/>";
219 else if (tariffs->Del(tariffToDel, currAdmin) == 0)
220     answer = "<DelTariff Result=\"Ok\"/>";
221 else
222     answer = "<DelTariff Result=\"Error. " + tariffs->GetStrError() + "\"/>";
223 }
224 //-----------------------------------------------------------------------------
225 //-----------------------------------------------------------------------------
226 //  CHG TARIFF
227 //-----------------------------------------------------------------------------
228 //-----------------------------------------------------------------------------
229 int PARSER_CHG_TARIFF::ParseSlashedIntParams(int paramsNum, const std::string & s, int * params)
230 {
231 char * str = new char[s.size() + 1];
232 char * p;
233 strcpy(str, s.c_str());
234 p = strtok(str, "/");
235
236 for (int i = 0; i < paramsNum; i++)
237     {
238     if (p == NULL)
239         {
240         delete[] str;
241         return -1;
242         }
243
244     if (str2x(p, params[i]) != 0)
245         {
246         delete[] str;
247         return -1;
248         }
249
250     p = strtok(NULL, "/");
251     }
252
253 delete[] str;
254 return 0;
255 }
256 //-----------------------------------------------------------------------------
257 int PARSER_CHG_TARIFF::ParseSlashedDoubleParams(int paramsNum, const std::string & s, double * params)
258 {
259 char * str = new char[s.size() + 1];
260 char * p;
261 strcpy(str, s.c_str());
262 p = strtok(str, "/");
263
264 for (int i = 0; i < paramsNum; i++)
265     {
266     if (p == NULL)
267         {
268         delete[] str;
269         return -1;
270         }
271
272     if (strtodouble2(p, params[i]) != 0)
273         {
274         delete[] str;
275         return -1;
276         }
277
278     p = strtok(NULL, "/");
279     }
280
281 delete[] str;
282 return 0;
283 }
284 //-----------------------------------------------------------------------------
285 int PARSER_CHG_TARIFF::ParseStart(void *, const char * el, const char ** attr)
286 {
287 double price[DIR_NUM];
288 int t[DIR_NUM];
289 depth++;
290
291 if (depth == 1)
292     {
293     if (strcasecmp(el, "SetTariff") == 0)
294         {
295         td.tariffConf.name = attr[1];
296         return 0;
297         }
298     }
299 else
300     {
301     std::string s;
302
303     if (strcasecmp(el, "PriceDayA") == 0)
304         {
305         s = attr[1];
306         if (ParseSlashedDoubleParams(DIR_NUM, s, price) == 0)
307             for (int j = 0; j < DIR_NUM; j++)
308                 td.dirPrice[j].priceDayA = price[j] / pt_mega;
309         return 0;
310         }
311
312     if (strcasecmp(el, "PriceDayB") == 0)
313         {
314         s = attr[1];
315         if (ParseSlashedDoubleParams(DIR_NUM, s, price) == 0)
316             for (int j = 0; j < DIR_NUM; j++)
317                 td.dirPrice[j].priceDayB = price[j] / pt_mega;
318         return 0;
319         }
320
321
322     if (strcasecmp(el, "PriceNightA") == 0)
323         {
324         s = attr[1];
325         if (ParseSlashedDoubleParams(DIR_NUM, s, price) == 0)
326             for (int j = 0; j < DIR_NUM; j++)
327                 td.dirPrice[j].priceNightA = price[j] / pt_mega;
328         return 0;
329         }
330
331     if (strcasecmp(el, "PriceNightB") == 0)
332         {
333         s = attr[1];
334         if (ParseSlashedDoubleParams(DIR_NUM, s, price) == 0)
335             for (int j = 0; j < DIR_NUM; j++)
336                 td.dirPrice[j].priceNightB = price[j] / pt_mega;
337         return 0;
338         }
339
340     if (strcasecmp(el, "Threshold") == 0)
341         {
342         s = attr[1];
343         if (ParseSlashedIntParams(DIR_NUM, s, t) == 0)
344             for (int j = 0; j < DIR_NUM; j++)
345                 td.dirPrice[j].threshold = t[j];
346         return 0;
347         }
348
349     if (strcasecmp(el, "SinglePrice") == 0)
350         {
351         s = attr[1];
352         if (ParseSlashedIntParams(DIR_NUM, s, t) == 0)
353             for (int j = 0; j < DIR_NUM; j++)
354                 td.dirPrice[j].singlePrice = t[j];
355         return 0;
356         }
357
358     if (strcasecmp(el, "NoDiscount") == 0)
359         {
360         s = attr[1];
361         if (ParseSlashedIntParams(DIR_NUM, s, t) == 0)
362             for (int j = 0; j < DIR_NUM; j++)
363                 td.dirPrice[j].noDiscount = t[j];
364         return 0;
365         }
366
367     for (int j = 0; j < DIR_NUM; j++)
368         {
369         char st[50];
370         snprintf(st, 50, "Time%d", j);
371         if (strcasecmp(el, st) == 0)
372             {
373             int h1 = 0;
374             int m1 = 0;
375             int h2 = 0;
376             int m2 = 0;
377             if (ParseTariffTimeStr(attr[1], h1, m1, h2, m2) == 0)
378                 {
379                 td.dirPrice[j].hDay = h1;
380                 td.dirPrice[j].mDay = m1;
381                 td.dirPrice[j].hNight = h2;
382                 td.dirPrice[j].mNight = m2;
383                 }
384             return 0;
385             }
386         }
387
388     if (strcasecmp(el, "Fee") == 0)
389         {
390         double fee;
391         if (strtodouble2(attr[1], fee) == 0)
392             td.tariffConf.fee = fee;
393         return 0;
394         }
395
396     if (strcasecmp(el, "PassiveCost") == 0)
397         {
398         double pc;
399         if (strtodouble2(attr[1], pc) == 0)
400             td.tariffConf.passiveCost = pc;
401         return 0;
402         }
403     if (strcasecmp(el, "Free") == 0)
404         {
405         double free;
406         if (strtodouble2(attr[1], free) == 0)
407             td.tariffConf.free = free;
408         return 0;
409         }
410
411     if (strcasecmp(el, "TraffType") == 0)
412         {
413         if (strcasecmp(attr[1], "up") == 0)
414             {
415             td.tariffConf.traffType = TRAFF_UP;
416             return 0;
417             }
418
419         if (strcasecmp(attr[1], "down") == 0)
420             {
421             td.tariffConf.traffType = TRAFF_DOWN;
422             return 0;
423             }
424         if (strcasecmp(attr[1], "up+down") == 0)
425             {
426             td.tariffConf.traffType = TRAFF_UP_DOWN;
427             return 0;
428             }
429         if (strcasecmp(attr[1], "max") == 0)
430             {
431             td.tariffConf.traffType = TRAFF_MAX;
432             return 0;
433             }
434         return 0;
435         }
436
437     if (strcasecmp(el, "Period") == 0)
438         {
439         td.tariffConf.period = TARIFF::StringToPeriod(attr[1]);
440         return 0;
441         }
442     }
443 return -1;
444 }
445 //-----------------------------------------------------------------------------
446 int PARSER_CHG_TARIFF::ParseEnd(void *, const char * el)
447 {
448 if (depth == 1)
449     {
450     if (strcasecmp(el, "SetTariff") == 0)
451         {
452         CreateAnswer();
453         depth--;
454         return 0;
455         }
456     }
457
458 depth--;
459 return -1;
460 }
461 //-----------------------------------------------------------------------------
462 void PARSER_CHG_TARIFF::CreateAnswer()
463 {
464 if (!td.tariffConf.name.data().empty())
465     {
466     TARIFF_DATA tariffData = td.GetData();
467     if (tariffs->Chg(tariffData, currAdmin) == 0)
468         {
469         answer = "<SetTariff Result=\"ok\"/>";
470         return;
471         }
472     else
473         {
474         answer = "<SetTariff Result=\"Change tariff error! " + tariffs->GetStrError() + "\"/>";
475         return;
476         }
477     }
478 answer = "<SetTariff Result=\"Change tariff error!\"/>";
479 }
480 //-----------------------------------------------------------------------------