MythTV master
mythfilldatabase.cpp
Go to the documentation of this file.
1// C headers
2#include <unistd.h>
3
4// C++ headers
5#include <iostream>
6
7// Qt headers
8#include <QtGlobal>
9#include <QCoreApplication>
10#include <QFileInfo>
11
12// MythTV headers
13#include "libmyth/mythcontext.h"
16#include "libmythbase/mythconfig.h"
19#include "libmythbase/mythdb.h"
23#include "libmythbase/mythversion.h"
24#include "libmythtv/dbcheck.h"
27#include "libmythtv/videosource.h" // for is_grabber..
28
29// filldata headers
30#include "filldata.h"
32
33int main(int argc, char *argv[])
34{
35 FillData fill_data;
36 int fromfile_id = 1;
37 QString fromfile_name;
38 bool from_file = false;
39 bool mark_repeats = true;
40
41 int sourceid = -1;
42
44 if (!cmdline.Parse(argc, argv))
45 {
48 }
49
50 if (cmdline.toBool("showhelp"))
51 {
53 return GENERIC_EXIT_OK;
54 }
55
56 if (cmdline.toBool("showversion"))
57 {
59 return GENERIC_EXIT_OK;
60 }
61
62 QCoreApplication a(argc, argv);
63 QCoreApplication::setApplicationName(MYTH_APPNAME_MYTHFILLDATABASE);
64
65 myth_nice(19);
66
67 int retval = cmdline.ConfigureLogging();
68 if (retval != GENERIC_EXIT_OK)
69 return retval;
70
71 if (cmdline.toBool("manual"))
72 {
73 std::cout << "###\n";
74 std::cout << "### Running in manual channel configuration mode.\n";
75 std::cout << "### This will ask you questions about every channel.\n";
76 std::cout << "###\n";
77 fill_data.m_chanData.m_interactive = true;
78 }
79
80 if (cmdline.toBool("onlyguide"))
81 {
82 LOG(VB_GENERAL, LOG_NOTICE,
83 "Only updating guide data, channel and icon updates will be ignored");
84 fill_data.m_chanData.m_guideDataOnly = true;
85 }
86
87 if (cmdline.toBool("preset"))
88 {
89 std::cout << "###\n";
90 std::cout << "### Running in preset channel configuration mode.\n";
91 std::cout << "### This will assign channel ";
92 std::cout << "preset numbers to every channel.\n";
93 std::cout << "###\n";
94 fill_data.m_chanData.m_channelPreset = true;
95 }
96
97 if (cmdline.toBool("file"))
98 {
99 // manual file mode
100 if (!cmdline.toBool("sourceid") ||
101 !cmdline.toBool("xmlfile"))
102 {
103 std::cerr << "The --file option must be used in combination" << std::endl
104 << "with both --sourceid and --xmlfile." << std::endl;
106 }
107
108 fromfile_id = cmdline.toInt("sourceid");
109 fromfile_name = cmdline.toString("xmlfile");
110
111 LOG(VB_GENERAL, LOG_INFO,
112 "Bypassing grabbers, reading directly from file");
113 from_file = true;
114 }
115
116 if (cmdline.toBool("dochannelupdates"))
117 fill_data.m_chanData.m_channelUpdates = true;
118 if (cmdline.toBool("nofilterchannels"))
119 fill_data.m_chanData.m_filterNewChannels = false;
120 if (!cmdline.GetPassthrough().isEmpty())
121 fill_data.m_grabOptions = " " + cmdline.GetPassthrough();
122 if (cmdline.toBool("sourceid"))
123 sourceid = cmdline.toInt("sourceid");
124 if (cmdline.toBool("cardtype"))
125 {
126 if (!cmdline.toBool("sourceid"))
127 {
128 std::cerr << "The --cardtype option must be used in combination" << std::endl
129 << "with a --sourceid option." << std::endl;
131 }
132
133 fill_data.m_chanData.m_cardType = cmdline.toString("cardtype")
134 .trimmed().toUpper();
135 }
136 if (cmdline.toBool("maxdays") && cmdline.toInt("maxdays") > 0)
137 {
138 fill_data.m_maxDays = cmdline.toInt("maxdays");
139 if (fill_data.m_maxDays == 1)
140 fill_data.SetRefresh(0, true);
141 }
142
143 QStringList sl = cmdline.toStringList("refresh");
144 if (!sl.isEmpty())
145 {
146 for (const auto & item : std::as_const(sl))
147 {
148 QString warn = QString("Invalid entry in --refresh list: %1")
149 .arg(item);
150
151 bool enable = !item.contains("not");
152
153 if (item.contains("today"))
154 fill_data.SetRefresh(0, enable);
155 else if (item.contains("tomorrow"))
156 fill_data.SetRefresh(1, enable);
157 else if (item.contains("second"))
158 fill_data.SetRefresh(2, enable);
159 else if (item.contains("all"))
160 fill_data.SetRefresh(FillData::kRefreshAll, enable);
161 else if (item.contains("-"))
162 {
163 bool ok = false;
164 QStringList r = item.split("-");
165
166 uint lower = r[0].toUInt(&ok);
167 if (!ok)
168 {
169 std::cerr << warn.toLocal8Bit().constData() << std::endl;
170 return 0;
171 }
172
173 uint upper = r[1].toUInt(&ok);
174 if (!ok)
175 {
176 std::cerr << warn.toLocal8Bit().constData() << std::endl;
177 return 0;
178 }
179
180 if (lower > upper)
181 {
182 std::cerr << warn.toLocal8Bit().constData() << std::endl;
183 return 0;
184 }
185
186 for (uint j = lower; j <= upper; ++j)
187 fill_data.SetRefresh(j, true);
188 }
189 else
190 {
191 bool ok = false;
192 uint day = item.toUInt(&ok);
193 if (!ok)
194 {
195 std::cerr << warn.toLocal8Bit().constData() << std::endl;
196 return 0;
197 }
198
199 fill_data.SetRefresh(day, true);
200 }
201 }
202 }
203
204 if (cmdline.toBool("dontrefreshtba"))
205 fill_data.m_refreshTba = false;
206 if (cmdline.toBool("onlychannels"))
207 fill_data.m_onlyUpdateChannels = true;
208 if (cmdline.toBool("noallatonce"))
209 fill_data.m_noAllAtOnce = true;
210
211 mark_repeats = cmdline.toBool("markrepeats");
212
213 MythContext context {MYTH_BINARY_VERSION};
214 if (!context.Init(false))
215 {
216 LOG(VB_GENERAL, LOG_ERR, "Failed to init MythContext, exiting.");
218 }
219
220 setHttpProxy();
221
222 MythTranslation::load("mythfrontend");
223
224 if (!UpgradeTVDatabaseSchema(false))
225 {
226 LOG(VB_GENERAL, LOG_ERR, "Incorrect database schema");
228 }
229
230 if (gCoreContext->SafeConnectToMasterServer(true, false))
231 {
232 LOG(VB_GENERAL, LOG_INFO,
233 "Opening blocking connection to master backend");
234 }
235 else
236 {
237 LOG(VB_GENERAL, LOG_WARNING,
238 "Failed to connect to master backend. MythFillDatabase will "
239 "continue running but will be unable to prevent backend from "
240 "shutting down, or triggering a reschedule when complete.");
241 }
242
243 if (from_file)
244 {
245 QString status = QObject::tr("currently running.");
246 QDateTime GuideDataBefore;
247 QDateTime GuideDataAfter;
248
250 updateLastRunStatus(status);
251
253 query.prepare("SELECT MAX(endtime) FROM program p "
254 "LEFT JOIN channel c ON p.chanid=c.chanid "
255 "WHERE c.deleted IS NULL AND c.sourceid= :SRCID "
256 "AND manualid = 0 AND c.xmltvid != '';");
257 query.bindValue(":SRCID", fromfile_id);
258
259 if (query.exec() && query.next())
260 {
261 if (!query.isNull(0))
262 GuideDataBefore =
263 MythDate::fromString(query.value(0).toString());
264 }
265
266 if (!fill_data.GrabDataFromFile(fromfile_id, fromfile_name))
267 {
268 return GENERIC_EXIT_NOT_OK;
269 }
270
272
273 query.prepare("SELECT MAX(endtime) FROM program p "
274 "LEFT JOIN channel c ON p.chanid=c.chanid "
275 "WHERE c.deleted IS NULL AND c.sourceid= :SRCID "
276 "AND manualid = 0 AND c.xmltvid != '';");
277 query.bindValue(":SRCID", fromfile_id);
278
279 if (query.exec() && query.next())
280 {
281 if (!query.isNull(0))
282 GuideDataAfter =
283 MythDate::fromString(query.value(0).toString());
284 }
285
286 if (GuideDataAfter == GuideDataBefore)
287 {
288 status = QObject::tr("mythfilldatabase ran, but did not insert "
289 "any new data into the Guide. This can indicate a "
290 "potential problem with the XML file used for the update.");
291 }
292 else
293 {
294 status = QObject::tr("Successful.");
295 }
296
297 updateLastRunStatus(status);
298 }
299 else
300 {
301 DataSourceList sourcelist;
302
303 MSqlQuery sourcequery(MSqlQuery::InitCon());
304 QString where;
305
306 if (sourceid != -1)
307 {
308 LOG(VB_GENERAL, LOG_INFO,
309 QString("Running for sourceid %1 ONLY because --sourceid "
310 "was given on command-line").arg(sourceid));
311 where = QString("WHERE sourceid = %1").arg(sourceid);
312 }
313
314 QString querystr = QString("SELECT sourceid,name,xmltvgrabber,userid,"
315 "password,lineupid "
316 "FROM videosource ") + where +
317 QString(" ORDER BY sourceid;");
318
319 if (sourcequery.exec(querystr))
320 {
321 if (sourcequery.size() > 0)
322 {
323 while (sourcequery.next())
324 {
325 DataSource newsource;
326
327 newsource.id = sourcequery.value(0).toInt();
328 newsource.name = sourcequery.value(1).toString();
329 newsource.xmltvgrabber = sourcequery.value(2).toString();
330 newsource.userid = sourcequery.value(3).toString();
331 newsource.password = sourcequery.value(4).toString();
332 newsource.lineupid = sourcequery.value(5).toString();
333
334 newsource.xmltvgrabber_baseline = false;
335 newsource.xmltvgrabber_manualconfig = false;
336 newsource.xmltvgrabber_cache = false;
337 newsource.xmltvgrabber_prefmethod = "";
338
339 sourcelist.push_back(newsource);
340 }
341 }
342 else
343 {
344 LOG(VB_GENERAL, LOG_ERR,
345 "There are no channel sources defined, did you run "
346 "the setup program?");
348 }
349 }
350 else
351 {
352 MythDB::DBError("loading channel sources", sourcequery);
354 }
355
356 if (!fill_data.Run(sourcelist))
357 LOG(VB_GENERAL, LOG_ERR, "Failed to fetch some program info");
358 else
359 LOG(VB_GENERAL, LOG_NOTICE, "Data fetching complete.");
360 }
361
362 if (fill_data.m_onlyUpdateChannels && !fill_data.m_needPostGrabProc)
363 {
364 return GENERIC_EXIT_OK;
365 }
366
367 LOG(VB_GENERAL, LOG_INFO, "Adjusting program database end times.");
368 int update_count = ProgramData::fix_end_times();
369 if (update_count == -1)
370 LOG(VB_GENERAL, LOG_ERR, "fix_end_times failed!");
371 else
372 LOG(VB_GENERAL, LOG_INFO,
373 QString(" %1 replacements made").arg(update_count));
374
375 LOG(VB_GENERAL, LOG_INFO, "Marking generic episodes.");
376
378 query.prepare("UPDATE program SET generic = 1 WHERE "
379 "((programid = '' AND subtitle = '' AND description = '') OR "
380 " (programid <> '' AND category_type = 'series' AND "
381 " program.programid LIKE '%0000'));");
382
383 if (!query.exec())
384 MythDB::DBError("mark generic", query);
385 else
386 LOG(VB_GENERAL, LOG_INFO,
387 QString(" Found %1").arg(query.numRowsAffected()));
388
389 LOG(VB_GENERAL, LOG_INFO, "Extending non-unique programids "
390 "with multiple parts.");
391
392 int found = 0;
394 sel.prepare("SELECT DISTINCT programid, partnumber, parttotal "
395 "FROM program WHERE partnumber > 0 AND parttotal > 0 AND "
396 "programid LIKE '%0000'");
397 if (sel.exec())
398 {
400 repl.prepare("UPDATE program SET programid = :NEWID "
401 "WHERE programid = :OLDID AND "
402 "partnumber = :PARTNUM AND "
403 "parttotal = :PARTTOTAL");
404
405 while (sel.next())
406 {
407 QString orig_programid = sel.value(0).toString();
408 QString new_programid = orig_programid.left(10);
409 QString part;
410
411 int partnum = sel.value(1).toInt();
412 int parttotal = sel.value(2).toInt();
413
414 part.setNum(parttotal);
415 new_programid.append(part.rightJustified(2, '0'));
416 part.setNum(partnum);
417 new_programid.append(part.rightJustified(2, '0'));
418
419 LOG(VB_GENERAL, LOG_INFO,
420 QString(" %1 -> %2 (part %3 of %4)")
421 .arg(orig_programid, new_programid)
422 .arg(partnum).arg(parttotal));
423
424 repl.bindValue(":NEWID", new_programid);
425 repl.bindValue(":OLDID", orig_programid);
426 repl.bindValue(":PARTNUM", partnum);
427 repl.bindValue(":PARTTOTAL", parttotal);
428 if (!repl.exec())
429 {
430 LOG(VB_GENERAL, LOG_INFO,
431 QString("Fudging programid from '%1' to '%2'")
432 .arg(orig_programid, new_programid));
433 }
434 else
435 {
436 found += repl.numRowsAffected();
437 }
438 }
439 }
440
441 LOG(VB_GENERAL, LOG_INFO, QString(" Found %1").arg(found));
442
443 LOG(VB_GENERAL, LOG_INFO, "Fixing missing original airdates.");
444 query.prepare("UPDATE program p "
445 "JOIN ( "
446 " SELECT programid, MAX(originalairdate) maxoad "
447 " FROM program "
448 " WHERE programid <> '' AND "
449 " originalairdate IS NOT NULL "
450 " GROUP BY programid ) oad "
451 " ON p.programid = oad.programid "
452 "SET p.originalairdate = oad.maxoad "
453 "WHERE p.originalairdate IS NULL");
454
455 if (query.exec())
456 {
457 LOG(VB_GENERAL, LOG_INFO,
458 QString(" Found %1 with programids")
459 .arg(query.numRowsAffected()));
460 }
461
462 query.prepare("UPDATE program p "
463 "JOIN ( "
464 " SELECT title, subtitle, description, "
465 " MAX(originalairdate) maxoad "
466 " FROM program "
467 " WHERE programid = '' AND "
468 " originalairdate IS NOT NULL "
469 " GROUP BY title, subtitle, description ) oad "
470 " ON p.programid = '' AND "
471 " p.title = oad.title AND "
472 " p.subtitle = oad.subtitle AND "
473 " p.description = oad.description "
474 "SET p.originalairdate = oad.maxoad "
475 "WHERE p.originalairdate IS NULL");
476
477 if (query.exec())
478 {
479 LOG(VB_GENERAL, LOG_INFO,
480 QString(" Found %1 without programids")
481 .arg(query.numRowsAffected()));
482 }
483
484 if (mark_repeats)
485 {
486 LOG(VB_GENERAL, LOG_INFO, "Marking repeats.");
487
488 int newEpiWindow = gCoreContext->GetNumSetting( "NewEpisodeWindow", 14);
489
491 query2.prepare("UPDATE program SET previouslyshown = 1 "
492 "WHERE previouslyshown = 0 "
493 "AND originalairdate is not null "
494 "AND (to_days(starttime) - to_days(originalairdate)) "
495 " > :NEWWINDOW;");
496 query2.bindValue(":NEWWINDOW", newEpiWindow);
497
498 if (query2.exec())
499 LOG(VB_GENERAL, LOG_INFO,
500 QString(" Found %1").arg(query2.numRowsAffected()));
501
502 LOG(VB_GENERAL, LOG_INFO, "Unmarking new episode rebroadcast repeats.");
503 query2.prepare("UPDATE program SET previouslyshown = 0 "
504 "WHERE previouslyshown = 1 "
505 "AND originalairdate is not null "
506 "AND (to_days(starttime) - to_days(originalairdate)) "
507 " <= :NEWWINDOW;");
508 query2.bindValue(":NEWWINDOW", newEpiWindow);
509
510 if (query2.exec())
511 LOG(VB_GENERAL, LOG_INFO,
512 QString(" Found %1").arg(query2.numRowsAffected()));
513 }
514
515 // Mark first and last showings
517 updt.prepare("UPDATE program SET first = 0, last = 0;");
518 if (!updt.exec())
519 MythDB::DBError("Clearing first and last showings", updt);
520
521 LOG(VB_GENERAL, LOG_INFO, "Marking episode first showings.");
522 updt.prepare("UPDATE program "
523 "JOIN (SELECT MIN(p.starttime) AS starttime, p.programid "
524 " FROM program p, channel c "
525 " WHERE p.programid <> '' "
526 " AND p.chanid = c.chanid "
527 " AND c.deleted IS NULL "
528 " AND c.visible > 0 "
529 " GROUP BY p.programid "
530 " ) AS firsts "
531 "ON program.programid = firsts.programid "
532 " AND program.starttime = firsts.starttime "
533 "SET program.first=1;");
534 if (!updt.exec())
535 MythDB::DBError("Marking first showings by id", updt);
536 found = updt.numRowsAffected();
537
538 updt.prepare("UPDATE program "
539 "JOIN (SELECT MIN(p.starttime) AS starttime, p.title, p.subtitle, "
540 " LEFT(p.description, 1024) AS partdesc "
541 " FROM program p, channel c "
542 " WHERE p.programid = '' "
543 " AND p.chanid = c.chanid "
544 " AND c.deleted IS NULL "
545 " AND c.visible > 0 "
546 " GROUP BY p.title, p.subtitle, partdesc "
547 " ) AS firsts "
548 "ON program.starttime = firsts.starttime "
549 " AND program.title = firsts.title "
550 " AND program.subtitle = firsts.subtitle "
551 " AND LEFT(program.description, 1024) = firsts.partdesc "
552 "SET program.first = 1 "
553 "WHERE program.programid = '';");
554 if (!updt.exec())
555 MythDB::DBError("Marking first showings", updt);
556 found += updt.numRowsAffected();
557 LOG(VB_GENERAL, LOG_INFO, QString(" Found %1").arg(found));
558
559 LOG(VB_GENERAL, LOG_INFO, "Marking episode last showings.");
560 updt.prepare("UPDATE program "
561 "JOIN (SELECT MAX(p.starttime) AS starttime, p.programid "
562 " FROM program p, channel c "
563 " WHERE p.programid <> '' "
564 " AND p.chanid = c.chanid "
565 " AND c.deleted IS NULL "
566 " AND c.visible > 0 "
567 " GROUP BY p.programid "
568 " ) AS lasts "
569 "ON program.programid = lasts.programid "
570 " AND program.starttime = lasts.starttime "
571 "SET program.last=1;");
572 if (!updt.exec())
573 MythDB::DBError("Marking last showings by id", updt);
574 found = updt.numRowsAffected();
575
576 updt.prepare("UPDATE program "
577 "JOIN (SELECT MAX(p.starttime) AS starttime, p.title, p.subtitle, "
578 " LEFT(p.description, 1024) AS partdesc "
579 " FROM program p, channel c "
580 " WHERE p.programid = '' "
581 " AND p.chanid = c.chanid "
582 " AND c.deleted IS NULL "
583 " AND c.visible > 0 "
584 " GROUP BY p.title, p.subtitle, partdesc "
585 " ) AS lasts "
586 "ON program.starttime = lasts.starttime "
587 " AND program.title = lasts.title "
588 " AND program.subtitle = lasts.subtitle "
589 " AND LEFT(program.description, 1024) = lasts.partdesc "
590 "SET program.last = 1 "
591 "WHERE program.programid = '';");
592 if (!updt.exec())
593 MythDB::DBError("Marking last showings", updt);
594 found += updt.numRowsAffected();
595 LOG(VB_GENERAL, LOG_INFO, QString(" Found %1").arg(found));
596
597#if 1
598 // limit MSqlQuery's lifetime
600 query2.prepare("SELECT count(previouslyshown) "
601 "FROM program WHERE previouslyshown = 1;");
602 if (query2.exec() && query2.next())
603 {
604 if (query2.value(0).toInt() != 0)
605 gCoreContext->SaveSettingOnHost("HaveRepeats", "1", nullptr);
606 else
607 gCoreContext->SaveSettingOnHost("HaveRepeats", "0", nullptr);
608 }
609#endif
610
611 if (!cmdline.toBool("noresched"))
612 {
613 LOG(VB_GENERAL, LOG_INFO, "\n"
614 "===============================================================\n"
615 "| Attempting to contact the master backend for rescheduling. |\n"
616 "| If the master is not running, rescheduling will happen when |\n"
617 "| the master backend is restarted. |\n"
618 "===============================================================");
619
620 ScheduledRecording::RescheduleMatch(0, 0, 0, QDateTime(),
621 "MythFillDatabase");
622 }
623
624 gCoreContext->SendMessage("CLEAR_SETTINGS_CACHE");
625
626 gCoreContext->SendSystemEvent("MYTHFILLDATABASE_RAN");
627
628 LOG(VB_GENERAL, LOG_NOTICE, "mythfilldatabase run complete.");
629
630 return GENERIC_EXIT_OK;
631}
632
633/* vim: set expandtab tabstop=4 shiftwidth=4: */
bool m_interactive
Definition: channeldata.h:28
bool m_guideDataOnly
Definition: channeldata.h:29
bool m_channelPreset
Definition: channeldata.h:30
QString m_cardType
Definition: channeldata.h:33
bool m_filterNewChannels
Definition: channeldata.h:32
bool m_channelUpdates
Definition: channeldata.h:31
bool m_noAllAtOnce
Definition: filldata.h:75
void SetRefresh(int day, bool set)
Definition: filldata.cpp:69
QString m_grabOptions
Definition: filldata.h:66
bool m_onlyUpdateChannels
Definition: filldata.h:73
bool GrabDataFromFile(int id, const QString &filename)
Definition: filldata.cpp:87
uint m_maxDays
Definition: filldata.h:67
bool m_needPostGrabProc
Definition: filldata.h:72
bool Run(DataSourceList &sourcelist)
Goes through the sourcelist and updates its channels with program info grabbed with the associated gr...
Definition: filldata.cpp:245
bool m_refreshTba
Definition: filldata.h:71
ChannelData m_chanData
Definition: filldata.h:63
@ kRefreshAll
Definition: filldata.h:59
QSqlQuery wrapper that fetches a DB connection from the connection pool.
Definition: mythdbcon.h:128
bool prepare(const QString &query)
QSqlQuery::prepare() is not thread safe in Qt <= 3.3.2.
Definition: mythdbcon.cpp:837
bool isNull(int field) const
Definition: mythdbcon.h:219
QVariant value(int i) const
Definition: mythdbcon.h:204
int size(void) const
Definition: mythdbcon.h:214
int numRowsAffected() const
Definition: mythdbcon.h:217
bool exec(void)
Wrap QSqlQuery::exec() so we can display SQL.
Definition: mythdbcon.cpp:618
void bindValue(const QString &placeholder, const QVariant &val)
Add a single binding.
Definition: mythdbcon.cpp:888
bool next(void)
Wrap QSqlQuery::next() so we can display the query results.
Definition: mythdbcon.cpp:812
static MSqlQueryInfo InitCon(ConnectionReuse _reuse=kNormalConnection)
Only use this in combination with MSqlQuery constructor.
Definition: mythdbcon.cpp:550
bool toBool(const QString &key) const
Returns stored QVariant as a boolean.
int toInt(const QString &key) const
Returns stored QVariant as an integer, falling to default if not provided.
virtual bool Parse(int argc, const char *const *argv)
Loop through argv and populate arguments with values.
int ConfigureLogging(const QString &mask="general", bool progress=false)
Read in logging options and initialize the logging interface.
QString toString(const QString &key) const
Returns stored QVariant as a QString, falling to default if not provided.
QString GetPassthrough(void) const
Return any text supplied on the command line after a bare '–'.
static void PrintVersion(void)
Print application version information.
QStringList toStringList(const QString &key, const QString &sep="") const
Returns stored QVariant as a QStringList, falling to default if not provided.
void PrintHelp(void) const
Print command line option help.
Startup context for MythTV.
Definition: mythcontext.h:20
bool SafeConnectToMasterServer(bool blockingClient=true, bool openEventSocket=true)
void SendSystemEvent(const QString &msg)
bool SaveSettingOnHost(const QString &key, const QString &newValue, const QString &host)
void SendMessage(const QString &message)
int GetNumSetting(const QString &key, int defaultval=0)
static void DBError(const QString &where, const MSqlQuery &query)
Definition: mythdb.cpp:226
static void load(const QString &module_name)
Load a QTranslator for the user's preferred language.
static int fix_end_times(void)
static void RescheduleMatch(uint recordid, uint sourceid, uint mplexid, const QDateTime &maxstarttime, const QString &why)
unsigned int uint
Definition: compat.h:68
bool UpgradeTVDatabaseSchema(const bool upgradeAllowed, const bool upgradeIfNoUI, const bool informSystemd)
Called from outside dbcheck.cpp to update the schema.
Definition: dbcheck.cpp:362
@ GENERIC_EXIT_NO_MYTHCONTEXT
No MythContext available.
Definition: exitcodes.h:16
@ GENERIC_EXIT_DB_OUTOFDATE
Database needs upgrade.
Definition: exitcodes.h:19
@ GENERIC_EXIT_OK
Exited with no error.
Definition: exitcodes.h:13
@ GENERIC_EXIT_SETUP_ERROR
Incorrectly setup system.
Definition: exitcodes.h:24
@ GENERIC_EXIT_INVALID_CMDLINE
Command line parse error.
Definition: exitcodes.h:18
@ GENERIC_EXIT_DB_ERROR
Database error.
Definition: exitcodes.h:20
@ GENERIC_EXIT_NOT_OK
Exited with error.
Definition: exitcodes.h:14
bool updateLastRunStatus(QString &status)
Definition: filldata.cpp:54
bool updateLastRunEnd(void)
Definition: filldata.cpp:37
bool updateLastRunStart(void)
Definition: filldata.cpp:45
std::vector< DataSource > DataSourceList
Definition: filldata.h:40
static constexpr const char * MYTH_APPNAME_MYTHFILLDATABASE
Definition: mythappname.h:8
MythCoreContext * gCoreContext
This global variable contains the MythCoreContext instance for the app.
int main(int argc, char *argv[])
#define LOG(_MASK_, _LEVEL_, _QSTRING_)
Definition: mythlogging.h:39
void setHttpProxy(void)
Get network proxy settings from OS, and use for [Q]Http[Comms].
bool myth_nice(int val)
QDateTime fromString(const QString &dtstr)
Converts kFilename && kISODate formats to QDateTime.
Definition: mythdate.cpp:39
MythCommFlagCommandLineParser cmdline
bool xmltvgrabber_baseline
Definition: filldata.h:33
bool xmltvgrabber_cache
Definition: filldata.h:35
QString lineupid
Definition: filldata.h:32
QString xmltvgrabber
Definition: filldata.h:29
QString name
Definition: filldata.h:28
int id
Definition: filldata.h:27
QString userid
Definition: filldata.h:30
QString xmltvgrabber_prefmethod
Definition: filldata.h:38
QString password
Definition: filldata.h:31
bool xmltvgrabber_manualconfig
Definition: filldata.h:34