summaryrefslogtreecommitdiffstats
path: root/xbmc/utils/DatabaseUtils.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'xbmc/utils/DatabaseUtils.cpp')
-rw-r--r--xbmc/utils/DatabaseUtils.cpp745
1 files changed, 745 insertions, 0 deletions
diff --git a/xbmc/utils/DatabaseUtils.cpp b/xbmc/utils/DatabaseUtils.cpp
new file mode 100644
index 0000000..fdff052
--- /dev/null
+++ b/xbmc/utils/DatabaseUtils.cpp
@@ -0,0 +1,745 @@
1/*
2 * Copyright (C) 2012-2018 Team Kodi
3 * This file is part of Kodi - https://kodi.tv
4 *
5 * SPDX-License-Identifier: GPL-2.0-or-later
6 * See LICENSES/README.md for more information.
7 */
8
9#include "DatabaseUtils.h"
10
11#include "dbwrappers/dataset.h"
12#include "music/MusicDatabase.h"
13#include "utils/StringUtils.h"
14#include "utils/Variant.h"
15#include "utils/log.h"
16#include "video/VideoDatabase.h"
17
18#include <sstream>
19
20MediaType DatabaseUtils::MediaTypeFromVideoContentType(int videoContentType)
21{
22 VIDEODB_CONTENT_TYPE type = (VIDEODB_CONTENT_TYPE)videoContentType;
23 switch (type)
24 {
25 case VIDEODB_CONTENT_MOVIES:
26 return MediaTypeMovie;
27
28 case VIDEODB_CONTENT_MOVIE_SETS:
29 return MediaTypeVideoCollection;
30
31 case VIDEODB_CONTENT_TVSHOWS:
32 return MediaTypeTvShow;
33
34 case VIDEODB_CONTENT_EPISODES:
35 return MediaTypeEpisode;
36
37 case VIDEODB_CONTENT_MUSICVIDEOS:
38 return MediaTypeMusicVideo;
39
40 default:
41 break;
42 }
43
44 return MediaTypeNone;
45}
46
47std::string DatabaseUtils::GetField(Field field, const MediaType &mediaType, DatabaseQueryPart queryPart)
48{
49 if (field == FieldNone || mediaType == MediaTypeNone)
50 return "";
51
52 if (mediaType == MediaTypeAlbum)
53 {
54 if (field == FieldId) return "albumview.idAlbum";
55 else if (field == FieldAlbum) return "albumview.strAlbum";
56 else if (field == FieldArtist || field == FieldAlbumArtist) return "albumview.strArtists";
57 else if (field == FieldGenre)
58 return "albumview.strGenres";
59 else if (field == FieldYear)
60 return "albumview.strReleaseDate";
61 else if (field == FieldOrigYear || field == FieldOrigDate)
62 return "albumview.strOrigReleaseDate";
63 else if (field == FieldMoods) return "albumview.strMoods";
64 else if (field == FieldStyles) return "albumview.strStyles";
65 else if (field == FieldThemes) return "albumview.strThemes";
66 else if (field == FieldReview) return "albumview.strReview";
67 else if (field == FieldMusicLabel) return "albumview.strLabel";
68 else if (field == FieldAlbumType) return "albumview.strType";
69 else if (field == FieldCompilation) return "albumview.bCompilation";
70 else if (field == FieldRating) return "albumview.fRating";
71 else if (field == FieldVotes) return "albumview.iVotes";
72 else if (field == FieldUserRating) return "albumview.iUserrating";
73 else if (field == FieldDateAdded) return "albumview.dateAdded";
74 else if (field == FieldDateNew) return "albumview.dateNew";
75 else if (field == FieldDateModified) return "albumview.dateModified";
76 else if (field == FieldPlaycount) return "albumview.iTimesPlayed";
77 else if (field == FieldLastPlayed) return "albumview.lastPlayed";
78 else if (field == FieldTotalDiscs)
79 return "albumview.iDiscTotal";
80 else if (field == FieldAlbumStatus)
81 return "albumview.strReleaseStatus";
82 }
83 else if (mediaType == MediaTypeSong)
84 {
85 if (field == FieldId) return "songview.idSong";
86 else if (field == FieldTitle) return "songview.strTitle";
87 else if (field == FieldTrackNumber) return "songview.iTrack";
88 else if (field == FieldTime) return "songview.iDuration";
89 else if (field == FieldYear)
90 return "songview.strReleaseDate";
91 else if (field == FieldOrigYear || field == FieldOrigDate)
92 return "songview.strOrigReleaseDate";
93 else if (field == FieldFilename) return "songview.strFilename";
94 else if (field == FieldPlaycount) return "songview.iTimesPlayed";
95 else if (field == FieldStartOffset) return "songview.iStartOffset";
96 else if (field == FieldEndOffset) return "songview.iEndOffset";
97 else if (field == FieldLastPlayed) return "songview.lastPlayed";
98 else if (field == FieldRating) return "songview.rating";
99 else if (field == FieldVotes) return "songview.votes";
100 else if (field == FieldUserRating) return "songview.userrating";
101 else if (field == FieldComment) return "songview.comment";
102 else if (field == FieldMoods) return "songview.mood";
103 else if (field == FieldAlbum) return "songview.strAlbum";
104 else if (field == FieldPath) return "songview.strPath";
105 else if (field == FieldArtist || field == FieldAlbumArtist) return "songview.strArtists";
106 else if (field == FieldGenre)
107 return "songview.strGenres";
108 else if (field == FieldDateAdded) return "songview.dateAdded";
109 else if (field == FieldDateNew) return "songview.dateNew";
110 else if (field == FieldDateModified) return "songview.dateModified";
111
112 else if (field == FieldDiscTitle)
113 return "songview.strDiscSubtitle";
114 else if (field == FieldBPM)
115 return "songview.iBPM";
116 else if (field == FieldMusicBitRate)
117 return "songview.iBitRate";
118 else if (field == FieldSampleRate)
119 return "songview.iSampleRate";
120 else if (field == FieldNoOfChannels)
121 return "songview.iChannels";
122 }
123 else if (mediaType == MediaTypeArtist)
124 {
125 if (field == FieldId) return "artistview.idArtist";
126 else if (field == FieldArtistSort) return "artistview.strSortName";
127 else if (field == FieldArtist) return "artistview.strArtist";
128 else if (field == FieldArtistType) return "artistview.strType";
129 else if (field == FieldGender) return "artistview.strGender";
130 else if (field == FieldDisambiguation) return "artistview.strDisambiguation";
131 else if (field == FieldGenre) return "artistview.strGenres";
132 else if (field == FieldMoods) return "artistview.strMoods";
133 else if (field == FieldStyles) return "artistview.strStyles";
134 else if (field == FieldInstruments) return "artistview.strInstruments";
135 else if (field == FieldBiography) return "artistview.strBiography";
136 else if (field == FieldBorn) return "artistview.strBorn";
137 else if (field == FieldBandFormed) return "artistview.strFormed";
138 else if (field == FieldDisbanded) return "artistview.strDisbanded";
139 else if (field == FieldDied) return "artistview.strDied";
140 else if (field == FieldDateAdded) return "artistview.dateAdded";
141 else if (field == FieldDateNew) return "artistview.dateNew";
142 else if (field == FieldDateModified) return "artistview.dateModified";
143 }
144 else if (mediaType == MediaTypeMusicVideo)
145 {
146 std::string result;
147 if (field == FieldId) return "musicvideo_view.idMVideo";
148 else if (field == FieldTitle) result = StringUtils::Format("musicvideo_view.c%02d",VIDEODB_ID_MUSICVIDEO_TITLE);
149 else if (field == FieldTime) result = StringUtils::Format("musicvideo_view.c%02d", VIDEODB_ID_MUSICVIDEO_RUNTIME);
150 else if (field == FieldDirector) result = StringUtils::Format("musicvideo_view.c%02d", VIDEODB_ID_MUSICVIDEO_DIRECTOR);
151 else if (field == FieldStudio) result = StringUtils::Format("musicvideo_view.c%02d", VIDEODB_ID_MUSICVIDEO_STUDIOS);
152 else if (field == FieldYear) return "musicvideo_view.premiered";
153 else if (field == FieldPlot) result = StringUtils::Format("musicvideo_view.c%02d", VIDEODB_ID_MUSICVIDEO_PLOT);
154 else if (field == FieldAlbum) result = StringUtils::Format("musicvideo_view.c%02d",VIDEODB_ID_MUSICVIDEO_ALBUM);
155 else if (field == FieldArtist) result = StringUtils::Format("musicvideo_view.c%02d", VIDEODB_ID_MUSICVIDEO_ARTIST);
156 else if (field == FieldGenre) result = StringUtils::Format("musicvideo_view.c%02d", VIDEODB_ID_MUSICVIDEO_GENRE);
157 else if (field == FieldTrackNumber) result = StringUtils::Format("musicvideo_view.c%02d", VIDEODB_ID_MUSICVIDEO_TRACK);
158 else if (field == FieldFilename) return "musicvideo_view.strFilename";
159 else if (field == FieldPath) return "musicvideo_view.strPath";
160 else if (field == FieldPlaycount) return "musicvideo_view.playCount";
161 else if (field == FieldLastPlayed) return "musicvideo_view.lastPlayed";
162 else if (field == FieldDateAdded) return "musicvideo_view.dateAdded";
163 else if (field == FieldUserRating) return "musicvideo_view.userrating";
164
165 if (!result.empty())
166 return result;
167 }
168 else if (mediaType == MediaTypeMovie)
169 {
170 std::string result;
171 if (field == FieldId) return "movie_view.idMovie";
172 else if (field == FieldTitle)
173 {
174 // We need some extra logic to get the title value if sorttitle isn't set
175 if (queryPart == DatabaseQueryPartOrderBy)
176 result = StringUtils::Format("CASE WHEN length(movie_view.c%02d) > 0 THEN movie_view.c%02d ELSE movie_view.c%02d END", VIDEODB_ID_SORTTITLE, VIDEODB_ID_SORTTITLE, VIDEODB_ID_TITLE);
177 else
178 result = StringUtils::Format("movie_view.c%02d", VIDEODB_ID_TITLE);
179 }
180 else if (field == FieldPlot) result = StringUtils::Format("movie_view.c%02d", VIDEODB_ID_PLOT);
181 else if (field == FieldPlotOutline) result = StringUtils::Format("movie_view.c%02d", VIDEODB_ID_PLOTOUTLINE);
182 else if (field == FieldTagline) result = StringUtils::Format("movie_view.c%02d", VIDEODB_ID_TAGLINE);
183 else if (field == FieldVotes) return "movie_view.votes";
184 else if (field == FieldRating) return "movie_view.rating";
185 else if (field == FieldWriter) result = StringUtils::Format("movie_view.c%02d", VIDEODB_ID_CREDITS);
186 else if (field == FieldYear) return "movie_view.premiered";
187 else if (field == FieldSortTitle) result = StringUtils::Format("movie_view.c%02d", VIDEODB_ID_SORTTITLE);
188 else if (field == FieldOriginalTitle) result = StringUtils::Format("movie_view.c%02d", VIDEODB_ID_ORIGINALTITLE);
189 else if (field == FieldTime) result = StringUtils::Format("movie_view.c%02d", VIDEODB_ID_RUNTIME);
190 else if (field == FieldMPAA) result = StringUtils::Format("movie_view.c%02d", VIDEODB_ID_MPAA);
191 else if (field == FieldTop250) result = StringUtils::Format("movie_view.c%02d", VIDEODB_ID_TOP250);
192 else if (field == FieldSet) return "movie_view.strSet";
193 else if (field == FieldGenre) result = StringUtils::Format("movie_view.c%02d", VIDEODB_ID_GENRE);
194 else if (field == FieldDirector) result = StringUtils::Format("movie_view.c%02d", VIDEODB_ID_DIRECTOR);
195 else if (field == FieldStudio) result = StringUtils::Format("movie_view.c%02d", VIDEODB_ID_STUDIOS);
196 else if (field == FieldTrailer) result = StringUtils::Format("movie_view.c%02d", VIDEODB_ID_TRAILER);
197 else if (field == FieldCountry) result = StringUtils::Format("movie_view.c%02d", VIDEODB_ID_COUNTRY);
198 else if (field == FieldFilename) return "movie_view.strFilename";
199 else if (field == FieldPath) return "movie_view.strPath";
200 else if (field == FieldPlaycount) return "movie_view.playCount";
201 else if (field == FieldLastPlayed) return "movie_view.lastPlayed";
202 else if (field == FieldDateAdded) return "movie_view.dateAdded";
203 else if (field == FieldUserRating) return "movie_view.userrating";
204
205 if (!result.empty())
206 return result;
207 }
208 else if (mediaType == MediaTypeTvShow)
209 {
210 std::string result;
211 if (field == FieldId) return "tvshow_view.idShow";
212 else if (field == FieldTitle)
213 {
214 // We need some extra logic to get the title value if sorttitle isn't set
215 if (queryPart == DatabaseQueryPartOrderBy)
216 result = StringUtils::Format("CASE WHEN length(tvshow_view.c%02d) > 0 THEN tvshow_view.c%02d ELSE tvshow_view.c%02d END", VIDEODB_ID_TV_SORTTITLE, VIDEODB_ID_TV_SORTTITLE, VIDEODB_ID_TV_TITLE);
217 else
218 result = StringUtils::Format("tvshow_view.c%02d", VIDEODB_ID_TV_TITLE);
219 }
220 else if (field == FieldPlot) result = StringUtils::Format("tvshow_view.c%02d", VIDEODB_ID_TV_PLOT);
221 else if (field == FieldTvShowStatus) result = StringUtils::Format("tvshow_view.c%02d", VIDEODB_ID_TV_STATUS);
222 else if (field == FieldVotes) return "tvshow_view.votes";
223 else if (field == FieldRating) return "tvshow_view.rating";
224 else if (field == FieldYear) result = StringUtils::Format("tvshow_view.c%02d", VIDEODB_ID_TV_PREMIERED);
225 else if (field == FieldGenre) result = StringUtils::Format("tvshow_view.c%02d", VIDEODB_ID_TV_GENRE);
226 else if (field == FieldMPAA) result = StringUtils::Format("tvshow_view.c%02d", VIDEODB_ID_TV_MPAA);
227 else if (field == FieldStudio) result = StringUtils::Format("tvshow_view.c%02d", VIDEODB_ID_TV_STUDIOS);
228 else if (field == FieldSortTitle) result = StringUtils::Format("tvshow_view.c%02d", VIDEODB_ID_TV_SORTTITLE);
229 else if (field == FieldOriginalTitle) result = StringUtils::Format("tvshow_view.c%02d", VIDEODB_ID_TV_ORIGINALTITLE);
230 else if (field == FieldPath) return "tvshow_view.strPath";
231 else if (field == FieldDateAdded) return "tvshow_view.dateAdded";
232 else if (field == FieldLastPlayed) return "tvshow_view.lastPlayed";
233 else if (field == FieldSeason) return "tvshow_view.totalSeasons";
234 else if (field == FieldNumberOfEpisodes) return "tvshow_view.totalCount";
235 else if (field == FieldNumberOfWatchedEpisodes) return "tvshow_view.watchedcount";
236 else if (field == FieldUserRating) return "tvshow_view.userrating";
237
238 if (!result.empty())
239 return result;
240 }
241 else if (mediaType == MediaTypeEpisode)
242 {
243 std::string result;
244 if (field == FieldId) return "episode_view.idEpisode";
245 else if (field == FieldTitle) result = StringUtils::Format("episode_view.c%02d", VIDEODB_ID_EPISODE_TITLE);
246 else if (field == FieldPlot) result = StringUtils::Format("episode_view.c%02d", VIDEODB_ID_EPISODE_PLOT);
247 else if (field == FieldVotes) return "episode_view.votes";
248 else if (field == FieldRating) return "episode_view.rating";
249 else if (field == FieldWriter) result = StringUtils::Format("episode_view.c%02d", VIDEODB_ID_EPISODE_CREDITS);
250 else if (field == FieldAirDate) result = StringUtils::Format("episode_view.c%02d", VIDEODB_ID_EPISODE_AIRED);
251 else if (field == FieldTime) result = StringUtils::Format("episode_view.c%02d", VIDEODB_ID_EPISODE_RUNTIME);
252 else if (field == FieldDirector) result = StringUtils::Format("episode_view.c%02d", VIDEODB_ID_EPISODE_DIRECTOR);
253 else if (field == FieldSeason) result = StringUtils::Format("episode_view.c%02d", VIDEODB_ID_EPISODE_SEASON);
254 else if (field == FieldEpisodeNumber) result = StringUtils::Format("episode_view.c%02d", VIDEODB_ID_EPISODE_EPISODE);
255 else if (field == FieldUniqueId) result = StringUtils::Format("episode_view.c%02d", VIDEODB_ID_EPISODE_IDENT_ID);
256 else if (field == FieldEpisodeNumberSpecialSort) result = StringUtils::Format("episode_view.c%02d", VIDEODB_ID_EPISODE_SORTEPISODE);
257 else if (field == FieldSeasonSpecialSort) result = StringUtils::Format("episode_view.c%02d", VIDEODB_ID_EPISODE_SORTSEASON);
258 else if (field == FieldFilename) return "episode_view.strFilename";
259 else if (field == FieldPath) return "episode_view.strPath";
260 else if (field == FieldPlaycount) return "episode_view.playCount";
261 else if (field == FieldLastPlayed) return "episode_view.lastPlayed";
262 else if (field == FieldDateAdded) return "episode_view.dateAdded";
263 else if (field == FieldTvShowTitle) return "episode_view.strTitle";
264 else if (field == FieldYear) return "episode_view.premiered";
265 else if (field == FieldMPAA) return "episode_view.mpaa";
266 else if (field == FieldStudio) return "episode_view.strStudio";
267 else if (field == FieldUserRating) return "episode_view.userrating";
268
269 if (!result.empty())
270 return result;
271 }
272
273 if (field == FieldRandom && queryPart == DatabaseQueryPartOrderBy)
274 return "RANDOM()";
275
276 return "";
277}
278
279int DatabaseUtils::GetField(Field field, const MediaType &mediaType)
280{
281 if (field == FieldNone || mediaType == MediaTypeNone)
282 return -1;
283
284 return GetField(field, mediaType, false);
285}
286
287int DatabaseUtils::GetFieldIndex(Field field, const MediaType &mediaType)
288{
289 if (field == FieldNone || mediaType == MediaTypeNone)
290 return -1;
291
292 return GetField(field, mediaType, true);
293}
294
295bool DatabaseUtils::GetSelectFields(const Fields &fields, const MediaType &mediaType, FieldList &selectFields)
296{
297 if (mediaType == MediaTypeNone || fields.empty())
298 return false;
299
300 Fields sortFields = fields;
301
302 // add necessary fields to create the label
303 if (mediaType == MediaTypeSong || mediaType == MediaTypeVideo || mediaType == MediaTypeVideoCollection ||
304 mediaType == MediaTypeMusicVideo || mediaType == MediaTypeMovie || mediaType == MediaTypeTvShow || mediaType == MediaTypeEpisode)
305 sortFields.insert(FieldTitle);
306 if (mediaType == MediaTypeEpisode)
307 {
308 sortFields.insert(FieldSeason);
309 sortFields.insert(FieldEpisodeNumber);
310 }
311 else if (mediaType == MediaTypeAlbum)
312 sortFields.insert(FieldAlbum);
313 else if (mediaType == MediaTypeSong)
314 sortFields.insert(FieldTrackNumber);
315 else if (mediaType == MediaTypeArtist)
316 sortFields.insert(FieldArtist);
317
318 selectFields.clear();
319 for (Fields::const_iterator it = sortFields.begin(); it != sortFields.end(); ++it)
320 {
321 // ignore FieldLabel because it needs special handling (see further up)
322 if (*it == FieldLabel)
323 continue;
324
325 if (GetField(*it, mediaType, DatabaseQueryPartSelect).empty())
326 {
327 CLog::Log(LOGDEBUG, "DatabaseUtils::GetSortFieldList: unknown field %d", *it);
328 continue;
329 }
330 selectFields.push_back(*it);
331 }
332
333 return !selectFields.empty();
334}
335
336bool DatabaseUtils::GetFieldValue(const dbiplus::field_value &fieldValue, CVariant &variantValue)
337{
338 if (fieldValue.get_isNull())
339 {
340 variantValue = CVariant::ConstNullVariant;
341 return true;
342 }
343
344 switch (fieldValue.get_fType())
345 {
346 case dbiplus::ft_String:
347 case dbiplus::ft_WideString:
348 case dbiplus::ft_Object:
349 variantValue = fieldValue.get_asString();
350 return true;
351 case dbiplus::ft_Char:
352 case dbiplus::ft_WChar:
353 variantValue = fieldValue.get_asChar();
354 return true;
355 case dbiplus::ft_Boolean:
356 variantValue = fieldValue.get_asBool();
357 return true;
358 case dbiplus::ft_Short:
359 variantValue = fieldValue.get_asShort();
360 return true;
361 case dbiplus::ft_UShort:
362 variantValue = fieldValue.get_asShort();
363 return true;
364 case dbiplus::ft_Int:
365 variantValue = fieldValue.get_asInt();
366 return true;
367 case dbiplus::ft_UInt:
368 variantValue = fieldValue.get_asUInt();
369 return true;
370 case dbiplus::ft_Float:
371 variantValue = fieldValue.get_asFloat();
372 return true;
373 case dbiplus::ft_Double:
374 case dbiplus::ft_LongDouble:
375 variantValue = fieldValue.get_asDouble();
376 return true;
377 case dbiplus::ft_Int64:
378 variantValue = fieldValue.get_asInt64();
379 return true;
380 }
381
382 return false;
383}
384
385bool DatabaseUtils::GetDatabaseResults(const MediaType &mediaType, const FieldList &fields, const std::unique_ptr<dbiplus::Dataset> &dataset, DatabaseResults &results)
386{
387 if (dataset->num_rows() == 0)
388 return true;
389
390 const dbiplus::result_set &resultSet = dataset->get_result_set();
391 unsigned int offset = results.size();
392
393 if (fields.empty())
394 {
395 DatabaseResult result;
396 for (unsigned int index = 0; index < resultSet.records.size(); index++)
397 {
398 result[FieldRow] = index + offset;
399 results.push_back(result);
400 }
401
402 return true;
403 }
404
405 if (resultSet.record_header.size() < fields.size())
406 return false;
407
408 std::vector<int> fieldIndexLookup;
409 fieldIndexLookup.reserve(fields.size());
410 for (FieldList::const_iterator it = fields.begin(); it != fields.end(); ++it)
411 fieldIndexLookup.push_back(GetFieldIndex(*it, mediaType));
412
413 results.reserve(resultSet.records.size() + offset);
414 for (unsigned int index = 0; index < resultSet.records.size(); index++)
415 {
416 DatabaseResult result;
417 result[FieldRow] = index + offset;
418
419 unsigned int lookupIndex = 0;
420 for (FieldList::const_iterator it = fields.begin(); it != fields.end(); ++it)
421 {
422 int fieldIndex = fieldIndexLookup[lookupIndex++];
423 if (fieldIndex < 0)
424 return false;
425
426 std::pair<Field, CVariant> value;
427 value.first = *it;
428 if (!GetFieldValue(resultSet.records[index]->at(fieldIndex), value.second))
429 CLog::Log(LOGWARNING, "GetDatabaseResults: unable to retrieve value of field %s", resultSet.record_header[fieldIndex].name.c_str());
430
431 if (value.first == FieldYear &&
432 (mediaType == MediaTypeTvShow || mediaType == MediaTypeEpisode))
433 {
434 CDateTime dateTime;
435 dateTime.SetFromDBDate(value.second.asString());
436 if (dateTime.IsValid())
437 {
438 value.second.clear();
439 value.second = dateTime.GetYear();
440 }
441 }
442
443 result.insert(value);
444 }
445
446 result[FieldMediaType] = mediaType;
447 if (mediaType == MediaTypeMovie || mediaType == MediaTypeVideoCollection ||
448 mediaType == MediaTypeTvShow || mediaType == MediaTypeMusicVideo)
449 result[FieldLabel] = result.at(FieldTitle).asString();
450 else if (mediaType == MediaTypeEpisode)
451 {
452 std::ostringstream label;
453 label << (int)(result.at(FieldSeason).asInteger() * 100 + result.at(FieldEpisodeNumber).asInteger());
454 label << ". ";
455 label << result.at(FieldTitle).asString();
456 result[FieldLabel] = label.str();
457 }
458 else if (mediaType == MediaTypeAlbum)
459 result[FieldLabel] = result.at(FieldAlbum).asString();
460 else if (mediaType == MediaTypeSong)
461 {
462 std::ostringstream label;
463 label << (int)result.at(FieldTrackNumber).asInteger();
464 label << ". ";
465 label << result.at(FieldTitle).asString();
466 result[FieldLabel] = label.str();
467 }
468 else if (mediaType == MediaTypeArtist)
469 result[FieldLabel] = result.at(FieldArtist).asString();
470
471 results.push_back(result);
472 }
473
474 return true;
475}
476
477std::string DatabaseUtils::BuildLimitClause(int end, int start /* = 0 */)
478{
479 return " LIMIT " + BuildLimitClauseOnly(end, start);
480}
481
482std::string DatabaseUtils::BuildLimitClauseOnly(int end, int start /* = 0 */)
483{
484 std::ostringstream sql;
485 if (start > 0)
486 {
487 if (end > 0)
488 {
489 end = end - start;
490 if (end < 0)
491 end = 0;
492 }
493
494 sql << start << "," << end;
495 }
496 else
497 sql << end;
498
499 return sql.str();
500}
501
502size_t DatabaseUtils::GetLimitCount(int end, int start)
503{
504 if (start > 0)
505 {
506 if (end - start < 0)
507 return 0;
508 else
509 return static_cast<size_t>(end - start);
510 }
511 else if (end > 0)
512 return static_cast<size_t>(end);
513 return 0;
514}
515
516int DatabaseUtils::GetField(Field field, const MediaType &mediaType, bool asIndex)
517{
518 if (field == FieldNone || mediaType == MediaTypeNone)
519 return -1;
520
521 int index = -1;
522
523 if (mediaType == MediaTypeAlbum)
524 {
525 if (field == FieldId) return CMusicDatabase::album_idAlbum;
526 else if (field == FieldAlbum) return CMusicDatabase::album_strAlbum;
527 else if (field == FieldArtist || field == FieldAlbumArtist) return CMusicDatabase::album_strArtists;
528 else if (field == FieldGenre) return CMusicDatabase::album_strGenres;
529 else if (field == FieldYear) return CMusicDatabase::album_strReleaseDate;
530 else if (field == FieldMoods) return CMusicDatabase::album_strMoods;
531 else if (field == FieldStyles) return CMusicDatabase::album_strStyles;
532 else if (field == FieldThemes) return CMusicDatabase::album_strThemes;
533 else if (field == FieldReview) return CMusicDatabase::album_strReview;
534 else if (field == FieldMusicLabel) return CMusicDatabase::album_strLabel;
535 else if (field == FieldAlbumType) return CMusicDatabase::album_strType;
536 else if (field == FieldRating) return CMusicDatabase::album_fRating;
537 else if (field == FieldVotes) return CMusicDatabase::album_iVotes;
538 else if (field == FieldUserRating) return CMusicDatabase::album_iUserrating;
539 else if (field == FieldPlaycount) return CMusicDatabase::album_iTimesPlayed;
540 else if (field == FieldLastPlayed) return CMusicDatabase::album_dtLastPlayed;
541 else if (field == FieldDateAdded) return CMusicDatabase::album_dateAdded;
542 else if (field == FieldDateNew) return CMusicDatabase::album_dateNew;
543 else if (field == FieldDateModified) return CMusicDatabase::album_dateModified;
544 else if (field == FieldTotalDiscs)
545 return CMusicDatabase::album_iTotalDiscs;
546 else if (field == FieldOrigYear || field == FieldOrigDate)
547 return CMusicDatabase::album_strOrigReleaseDate;
548 else if (field == FieldAlbumStatus)
549 return CMusicDatabase::album_strReleaseStatus;
550 }
551 else if (mediaType == MediaTypeSong)
552 {
553 if (field == FieldId) return CMusicDatabase::song_idSong;
554 else if (field == FieldTitle) return CMusicDatabase::song_strTitle;
555 else if (field == FieldTrackNumber) return CMusicDatabase::song_iTrack;
556 else if (field == FieldTime) return CMusicDatabase::song_iDuration;
557 else if (field == FieldYear) return CMusicDatabase::song_strReleaseDate;
558 else if (field == FieldFilename) return CMusicDatabase::song_strFileName;
559 else if (field == FieldPlaycount) return CMusicDatabase::song_iTimesPlayed;
560 else if (field == FieldStartOffset) return CMusicDatabase::song_iStartOffset;
561 else if (field == FieldEndOffset) return CMusicDatabase::song_iEndOffset;
562 else if (field == FieldLastPlayed) return CMusicDatabase::song_lastplayed;
563 else if (field == FieldRating) return CMusicDatabase::song_rating;
564 else if (field == FieldUserRating) return CMusicDatabase::song_userrating;
565 else if (field == FieldVotes) return CMusicDatabase::song_votes;
566 else if (field == FieldComment) return CMusicDatabase::song_comment;
567 else if (field == FieldMoods) return CMusicDatabase::song_mood;
568 else if (field == FieldAlbum) return CMusicDatabase::song_strAlbum;
569 else if (field == FieldPath) return CMusicDatabase::song_strPath;
570 else if (field == FieldGenre) return CMusicDatabase::song_strGenres;
571 else if (field == FieldArtist || field == FieldAlbumArtist) return CMusicDatabase::song_strArtists;
572 else if (field == FieldDateAdded) return CMusicDatabase::song_dateAdded;
573 else if (field == FieldDateNew) return CMusicDatabase::song_dateNew;
574 else if (field == FieldDateModified) return CMusicDatabase::song_dateModified;
575 else if (field == FieldBPM)
576 return CMusicDatabase::song_iBPM;
577 else if (field == FieldMusicBitRate)
578 return CMusicDatabase::song_iBitRate;
579 else if (field == FieldSampleRate)
580 return CMusicDatabase::song_iSampleRate;
581 else if (field == FieldNoOfChannels)
582 return CMusicDatabase::song_iChannels;
583 }
584 else if (mediaType == MediaTypeArtist)
585 {
586 if (field == FieldId) return CMusicDatabase::artist_idArtist;
587 else if (field == FieldArtist) return CMusicDatabase::artist_strArtist;
588 else if (field == FieldArtistSort) return CMusicDatabase::artist_strSortName;
589 else if (field == FieldArtistType) return CMusicDatabase::artist_strType;
590 else if (field == FieldGender) return CMusicDatabase::artist_strGender;
591 else if (field == FieldDisambiguation) return CMusicDatabase::artist_strDisambiguation;
592 else if (field == FieldGenre) return CMusicDatabase::artist_strGenres;
593 else if (field == FieldMoods) return CMusicDatabase::artist_strMoods;
594 else if (field == FieldStyles) return CMusicDatabase::artist_strStyles;
595 else if (field == FieldInstruments) return CMusicDatabase::artist_strInstruments;
596 else if (field == FieldBiography) return CMusicDatabase::artist_strBiography;
597 else if (field == FieldBorn) return CMusicDatabase::artist_strBorn;
598 else if (field == FieldBandFormed) return CMusicDatabase::artist_strFormed;
599 else if (field == FieldDisbanded) return CMusicDatabase::artist_strDisbanded;
600 else if (field == FieldDied) return CMusicDatabase::artist_strDied;
601 else if (field == FieldDateAdded) return CMusicDatabase::artist_dateAdded;
602 else if (field == FieldDateNew) return CMusicDatabase::artist_dateNew;
603 else if (field == FieldDateModified) return CMusicDatabase::artist_dateModified;
604 }
605 else if (mediaType == MediaTypeMusicVideo)
606 {
607 if (field == FieldId) return 0;
608 else if (field == FieldTitle) index = VIDEODB_ID_MUSICVIDEO_TITLE;
609 else if (field == FieldTime) index = VIDEODB_ID_MUSICVIDEO_RUNTIME;
610 else if (field == FieldDirector) index = VIDEODB_ID_MUSICVIDEO_DIRECTOR;
611 else if (field == FieldStudio) index = VIDEODB_ID_MUSICVIDEO_STUDIOS;
612 else if (field == FieldYear) return VIDEODB_DETAILS_MUSICVIDEO_PREMIERED;
613 else if (field == FieldPlot) index = VIDEODB_ID_MUSICVIDEO_PLOT;
614 else if (field == FieldAlbum) index = VIDEODB_ID_MUSICVIDEO_ALBUM;
615 else if (field == FieldArtist) index = VIDEODB_ID_MUSICVIDEO_ARTIST;
616 else if (field == FieldGenre) index = VIDEODB_ID_MUSICVIDEO_GENRE;
617 else if (field == FieldTrackNumber) index = VIDEODB_ID_MUSICVIDEO_TRACK;
618 else if (field == FieldFilename) return VIDEODB_DETAILS_MUSICVIDEO_FILE;
619 else if (field == FieldPath) return VIDEODB_DETAILS_MUSICVIDEO_PATH;
620 else if (field == FieldPlaycount) return VIDEODB_DETAILS_MUSICVIDEO_PLAYCOUNT;
621 else if (field == FieldLastPlayed) return VIDEODB_DETAILS_MUSICVIDEO_LASTPLAYED;
622 else if (field == FieldDateAdded) return VIDEODB_DETAILS_MUSICVIDEO_DATEADDED;
623 else if (field == FieldUserRating) return VIDEODB_DETAILS_MUSICVIDEO_USER_RATING;
624
625 if (index < 0)
626 return index;
627
628 if (asIndex)
629 {
630 // see VideoDatabase.h
631 // the first field is the item's ID and the second is the item's file ID
632 index += 2;
633 }
634 }
635 else if (mediaType == MediaTypeMovie)
636 {
637 if (field == FieldId) return 0;
638 else if (field == FieldTitle) index = VIDEODB_ID_TITLE;
639 else if (field == FieldSortTitle) index = VIDEODB_ID_SORTTITLE;
640 else if (field == FieldOriginalTitle) index = VIDEODB_ID_ORIGINALTITLE;
641 else if (field == FieldPlot) index = VIDEODB_ID_PLOT;
642 else if (field == FieldPlotOutline) index = VIDEODB_ID_PLOTOUTLINE;
643 else if (field == FieldTagline) index = VIDEODB_ID_TAGLINE;
644 else if (field == FieldVotes) return VIDEODB_DETAILS_MOVIE_VOTES;
645 else if (field == FieldRating) return VIDEODB_DETAILS_MOVIE_RATING;
646 else if (field == FieldWriter) index = VIDEODB_ID_CREDITS;
647 else if (field == FieldYear) return VIDEODB_DETAILS_MOVIE_PREMIERED;
648 else if (field == FieldTime) index = VIDEODB_ID_RUNTIME;
649 else if (field == FieldMPAA) index = VIDEODB_ID_MPAA;
650 else if (field == FieldTop250) index = VIDEODB_ID_TOP250;
651 else if (field == FieldSet) return VIDEODB_DETAILS_MOVIE_SET_NAME;
652 else if (field == FieldGenre) index = VIDEODB_ID_GENRE;
653 else if (field == FieldDirector) index = VIDEODB_ID_DIRECTOR;
654 else if (field == FieldStudio) index = VIDEODB_ID_STUDIOS;
655 else if (field == FieldTrailer) index = VIDEODB_ID_TRAILER;
656 else if (field == FieldCountry) index = VIDEODB_ID_COUNTRY;
657 else if (field == FieldFilename) index = VIDEODB_DETAILS_MOVIE_FILE;
658 else if (field == FieldPath) return VIDEODB_DETAILS_MOVIE_PATH;
659 else if (field == FieldPlaycount) return VIDEODB_DETAILS_MOVIE_PLAYCOUNT;
660 else if (field == FieldLastPlayed) return VIDEODB_DETAILS_MOVIE_LASTPLAYED;
661 else if (field == FieldDateAdded) return VIDEODB_DETAILS_MOVIE_DATEADDED;
662 else if (field == FieldUserRating) return VIDEODB_DETAILS_MOVIE_USER_RATING;
663
664 if (index < 0)
665 return index;
666
667 if (asIndex)
668 {
669 // see VideoDatabase.h
670 // the first field is the item's ID and the second is the item's file ID
671 index += 2;
672 }
673 }
674 else if (mediaType == MediaTypeTvShow)
675 {
676 if (field == FieldId) return 0;
677 else if (field == FieldTitle) index = VIDEODB_ID_TV_TITLE;
678 else if (field == FieldSortTitle) index = VIDEODB_ID_TV_SORTTITLE;
679 else if (field == FieldOriginalTitle) index = VIDEODB_ID_TV_ORIGINALTITLE;
680 else if (field == FieldPlot) index = VIDEODB_ID_TV_PLOT;
681 else if (field == FieldTvShowStatus) index = VIDEODB_ID_TV_STATUS;
682 else if (field == FieldVotes) return VIDEODB_DETAILS_TVSHOW_VOTES;
683 else if (field == FieldRating) return VIDEODB_DETAILS_TVSHOW_RATING;
684 else if (field == FieldYear) index = VIDEODB_ID_TV_PREMIERED;
685 else if (field == FieldGenre) index = VIDEODB_ID_TV_GENRE;
686 else if (field == FieldMPAA) index = VIDEODB_ID_TV_MPAA;
687 else if (field == FieldStudio) index = VIDEODB_ID_TV_STUDIOS;
688 else if (field == FieldPath) return VIDEODB_DETAILS_TVSHOW_PATH;
689 else if (field == FieldDateAdded) return VIDEODB_DETAILS_TVSHOW_DATEADDED;
690 else if (field == FieldLastPlayed) return VIDEODB_DETAILS_TVSHOW_LASTPLAYED;
691 else if (field == FieldNumberOfEpisodes) return VIDEODB_DETAILS_TVSHOW_NUM_EPISODES;
692 else if (field == FieldNumberOfWatchedEpisodes) return VIDEODB_DETAILS_TVSHOW_NUM_WATCHED;
693 else if (field == FieldSeason) return VIDEODB_DETAILS_TVSHOW_NUM_SEASONS;
694 else if (field == FieldUserRating) return VIDEODB_DETAILS_TVSHOW_USER_RATING;
695
696 if (index < 0)
697 return index;
698
699 if (asIndex)
700 {
701 // see VideoDatabase.h
702 // the first field is the item's ID
703 index += 1;
704 }
705 }
706 else if (mediaType == MediaTypeEpisode)
707 {
708 if (field == FieldId) return 0;
709 else if (field == FieldTitle) index = VIDEODB_ID_EPISODE_TITLE;
710 else if (field == FieldPlot) index = VIDEODB_ID_EPISODE_PLOT;
711 else if (field == FieldVotes) return VIDEODB_DETAILS_EPISODE_VOTES;
712 else if (field == FieldRating) return VIDEODB_DETAILS_EPISODE_RATING;
713 else if (field == FieldWriter) index = VIDEODB_ID_EPISODE_CREDITS;
714 else if (field == FieldAirDate) index = VIDEODB_ID_EPISODE_AIRED;
715 else if (field == FieldTime) index = VIDEODB_ID_EPISODE_RUNTIME;
716 else if (field == FieldDirector) index = VIDEODB_ID_EPISODE_DIRECTOR;
717 else if (field == FieldSeason) index = VIDEODB_ID_EPISODE_SEASON;
718 else if (field == FieldEpisodeNumber) index = VIDEODB_ID_EPISODE_EPISODE;
719 else if (field == FieldUniqueId) index = VIDEODB_ID_EPISODE_IDENT_ID;
720 else if (field == FieldEpisodeNumberSpecialSort) index = VIDEODB_ID_EPISODE_SORTEPISODE;
721 else if (field == FieldSeasonSpecialSort) index = VIDEODB_ID_EPISODE_SORTSEASON;
722 else if (field == FieldFilename) return VIDEODB_DETAILS_EPISODE_FILE;
723 else if (field == FieldPath) return VIDEODB_DETAILS_EPISODE_PATH;
724 else if (field == FieldPlaycount) return VIDEODB_DETAILS_EPISODE_PLAYCOUNT;
725 else if (field == FieldLastPlayed) return VIDEODB_DETAILS_EPISODE_LASTPLAYED;
726 else if (field == FieldDateAdded) return VIDEODB_DETAILS_EPISODE_DATEADDED;
727 else if (field == FieldTvShowTitle) return VIDEODB_DETAILS_EPISODE_TVSHOW_NAME;
728 else if (field == FieldStudio) return VIDEODB_DETAILS_EPISODE_TVSHOW_STUDIO;
729 else if (field == FieldYear) return VIDEODB_DETAILS_EPISODE_TVSHOW_AIRED;
730 else if (field == FieldMPAA) return VIDEODB_DETAILS_EPISODE_TVSHOW_MPAA;
731 else if (field == FieldUserRating) return VIDEODB_DETAILS_EPISODE_USER_RATING;
732
733 if (index < 0)
734 return index;
735
736 if (asIndex)
737 {
738 // see VideoDatabase.h
739 // the first field is the item's ID and the second is the item's file ID
740 index += 2;
741 }
742 }
743
744 return index;
745}