diff options
author | Jonathan Marshall <jmarshall@never.you.mind> | 2012-05-10 11:51:25 +1200 |
---|---|---|
committer | Jonathan Marshall <jmarshall@never.you.mind> | 2012-05-10 20:38:24 +1200 |
commit | 79011306ff02d3f38269efb09ce5f44cbde9f56c (patch) | |
tree | 02cd7022cc0c0e6f678163e2d7304e6ffe523b08 | |
parent | 7df84a0fcdafd049611a16158a9ca924c1dd82da (diff) |
introduce Filter class so as to break up joins/where/order in a nicer way for the videodb
-rw-r--r-- | xbmc/filesystem/SmartPlaylistDirectory.cpp | 29 | ||||
-rw-r--r-- | xbmc/interfaces/http-api/XBMChttp.cpp | 2 | ||||
-rw-r--r-- | xbmc/interfaces/json-rpc/VideoLibrary.cpp | 2 | ||||
-rw-r--r-- | xbmc/video/VideoDatabase.cpp | 298 | ||||
-rw-r--r-- | xbmc/video/VideoDatabase.h | 19 |
5 files changed, 236 insertions, 114 deletions
diff --git a/xbmc/filesystem/SmartPlaylistDirectory.cpp b/xbmc/filesystem/SmartPlaylistDirectory.cpp index e17f37938c..8cfd7cf7b1 100644 --- a/xbmc/filesystem/SmartPlaylistDirectory.cpp +++ b/xbmc/filesystem/SmartPlaylistDirectory.cpp @@ -56,8 +56,10 @@ namespace XFILE { CVideoDatabase db; db.Open(); - CStdString whereOrder = playlist.GetWhereClause(db, playlists) + " " + playlist.GetOrderClause(db); - success = db.GetTvShowsByWhere("videodb://2/2/", whereOrder, items); + CVideoDatabase::Filter filter; + filter.where = playlist.GetWhereClause(db, playlists); + filter.order = playlist.GetOrderClause(db); + success = db.GetTvShowsByWhere("videodb://2/2/", filter, items); items.SetContent("tvshows"); db.Close(); } @@ -65,8 +67,10 @@ namespace XFILE { CVideoDatabase db; db.Open(); - CStdString whereOrder = playlist.GetWhereClause(db, playlists) + " " + playlist.GetOrderClause(db); - success = db.GetEpisodesByWhere("videodb://2/2/", whereOrder, items); + CVideoDatabase::Filter filter; + filter.where = playlist.GetWhereClause(db, playlists); + filter.order = playlist.GetOrderClause(db); + success = db.GetEpisodesByWhere("videodb://2/2/", filter, items); items.SetContent("episodes"); db.Close(); } @@ -74,7 +78,10 @@ namespace XFILE { CVideoDatabase db; db.Open(); - success = db.GetMoviesByWhere("videodb://1/2/", playlist.GetWhereClause(db, playlists), playlist.GetOrderClause(db), items, true); + CVideoDatabase::Filter filter; + filter.where = playlist.GetWhereClause(db, playlists); + filter.order = playlist.GetOrderClause(db); + success = db.GetMoviesByWhere("videodb://1/2/", filter, items, true); items.SetContent("movies"); db.Close(); } @@ -108,18 +115,22 @@ namespace XFILE { CVideoDatabase db; db.Open(); - CStdString whereOrder; + CVideoDatabase::Filter filter; if (playlist.GetType().Equals("mixed")) { CSmartPlaylist mvidPlaylist(playlist); mvidPlaylist.SetType("musicvideos"); - whereOrder = mvidPlaylist.GetWhereClause(db, playlists) + " " + mvidPlaylist.GetOrderClause(db); + filter.where = mvidPlaylist.GetWhereClause(db, playlists); + filter.order = mvidPlaylist.GetOrderClause(db); } else - whereOrder = playlist.GetWhereClause(db, playlists) + " " + playlist.GetOrderClause(db); + { + filter.where = playlist.GetWhereClause(db, playlists); + filter.order = playlist.GetOrderClause(db); + } CFileItemList items2; - success2 = db.GetMusicVideosByWhere("videodb://3/2/", whereOrder, items2, false); // TODO: SMARTPLAYLISTS Don't check locks??? + success2 = db.GetMusicVideosByWhere("videodb://3/2/", filter, items2, false); // TODO: SMARTPLAYLISTS Don't check locks??? db.Close(); items.Append(items2); if (items2.Size()) diff --git a/xbmc/interfaces/http-api/XBMChttp.cpp b/xbmc/interfaces/http-api/XBMChttp.cpp index c3db3f2d51..7201ac6e13 100644 --- a/xbmc/interfaces/http-api/XBMChttp.cpp +++ b/xbmc/interfaces/http-api/XBMChttp.cpp @@ -1050,7 +1050,7 @@ int CXbmcHttp::xbmcAddToPlayListFromDB(int numParas, CStdString paras[]) return SetResponse(openTag+"Error: Could not open video database"); if (type.Equals("movies")) - videodatabase.GetMoviesByWhere("", where, "", filelist); + videodatabase.GetMoviesByWhere("", where, filelist); else if (type.Equals("episodes")) videodatabase.GetEpisodesByWhere("", where, filelist); else if (type.Equals("musicvideos")) diff --git a/xbmc/interfaces/json-rpc/VideoLibrary.cpp b/xbmc/interfaces/json-rpc/VideoLibrary.cpp index af1cb73c4e..c4241b90e9 100644 --- a/xbmc/interfaces/json-rpc/VideoLibrary.cpp +++ b/xbmc/interfaces/json-rpc/VideoLibrary.cpp @@ -35,7 +35,7 @@ JSONRPC_STATUS CVideoLibrary::GetMovies(const CStdString &method, ITransportLaye CFileItemList items; JSONRPC_STATUS ret = OK; - if (videodatabase.GetMoviesByWhere("videodb://1/", "", "", items)) + if (videodatabase.GetMoviesByWhere("videodb://1/", "", items)) ret = GetAdditionalMovieDetails(parameterObject, items, result, videodatabase); videodatabase.Close(); diff --git a/xbmc/video/VideoDatabase.cpp b/xbmc/video/VideoDatabase.cpp index 5d5892c5b8..86f9ff51f6 100644 --- a/xbmc/video/VideoDatabase.cpp +++ b/xbmc/video/VideoDatabase.cpp @@ -1548,32 +1548,35 @@ void CVideoDatabase::DeleteDetailsForTvShow(const CStdString& strPath, int idTvS //******************************************************************************************************************************** void CVideoDatabase::GetMoviesByActor(const CStdString& strActor, CFileItemList& items) { - CStdString where = PrepareSQL("LEFT JOIN actorlinkmovie ON actorlinkmovie.idMovie=movieview.idMovie " - "LEFT JOIN actors a ON a.idActor=actorlinkmovie.idActor " - "LEFT JOIN directorlinkmovie ON directorlinkmovie.idMovie=movieview.idMovie " - "LEFT JOIN actors d ON d.idActor=directorlinkmovie.idDirector " - "WHERE a.strActor='%s' OR d.strActor='%s' GROUP BY movieview.idMovie", strActor.c_str(), strActor.c_str()); - GetMoviesByWhere("videodb://1/2/", where, "", items); + Filter filter; + filter.join = PrepareSQL("LEFT JOIN actorlinkmovie ON actorlinkmovie.idMovie=movieview.idMovie " + "LEFT JOIN actors a ON a.idActor=actorlinkmovie.idActor " + "LEFT JOIN directorlinkmovie ON directorlinkmovie.idMovie=movieview.idMovie " + "LEFT JOIN actors d ON d.idActor=directorlinkmovie.idDirector"); + filter.where = PrepareSQL("WHERE a.strActor='%s' OR d.strActor='%s' GROUP BY movieview.idMovie", strActor.c_str(), strActor.c_str()); + GetMoviesByWhere("videodb://1/2/", filter, items); } void CVideoDatabase::GetTvShowsByActor(const CStdString& strActor, CFileItemList& items) { - CStdString where = PrepareSQL("LEFT JOIN actorlinktvshow ON actorlinktvshow.idShow=tvshowview.idShow " - "LEFT JOIN actors a ON a.idActor=actorlinktvshow.idActor " - "LEFT JOIN directorlinktvshow ON directorlinktvshow.idShow=tvshowview.idShow " - "LEFT JOIN actors d ON d.idActor=directorlinktvshow.idDirector " - "WHERE a.strActor='%s' OR d.strActor='%s' GROUP BY tvshowview.idShow", strActor.c_str(), strActor.c_str()); - GetTvShowsByWhere("videodb://2/2/", where, items); + Filter filter; + filter.join = PrepareSQL("LEFT JOIN actorlinktvshow ON actorlinktvshow.idShow=tvshowview.idShow " + "LEFT JOIN actors a ON a.idActor=actorlinktvshow.idActor " + "LEFT JOIN directorlinktvshow ON directorlinktvshow.idShow=tvshowview.idShow " + "LEFT JOIN actors d ON d.idActor=directorlinktvshow.idDirector"); + filter.where = PrepareSQL("WHERE a.strActor='%s' OR d.strActor='%s' GROUP BY tvshowview.idShow", strActor.c_str(), strActor.c_str()); + GetTvShowsByWhere("videodb://2/2/", filter, items); } void CVideoDatabase::GetEpisodesByActor(const CStdString& strActor, CFileItemList& items) { - CStdString where = PrepareSQL("LEFT JOIN actorlinkepisode ON actorlinkepisode.idEpisode=episodeview.idEpisode " - "LEFT JOIN actors a ON a.idActor=actorlinkepisode.idActor " - "LEFT JOIN directorlinkepisode ON directorlinkepisode.idEpisode=episodeview.idEpisode " - "LEFT JOIN actors d ON d.idActor=directorlinkepisode.idDirector " - "WHERE a.strActor='%s' OR d.strActor='%s' GROUP BY episodeview.idEpisode", strActor.c_str(), strActor.c_str()); - GetEpisodesByWhere("videodb://2/2/", where, items); + Filter filter; + filter.join = PrepareSQL("LEFT JOIN actorlinkepisode ON actorlinkepisode.idEpisode=episodeview.idEpisode " + "LEFT JOIN actors a ON a.idActor=actorlinkepisode.idActor " + "LEFT JOIN directorlinkepisode ON directorlinkepisode.idEpisode=episodeview.idEpisode " + "LEFT JOIN actors d ON d.idActor=directorlinkepisode.idDirector"); + filter.where = PrepareSQL("WHERE a.strActor='%s' OR d.strActor='%s' GROUP BY episodeview.idEpisode", strActor.c_str(), strActor.c_str()); + GetEpisodesByWhere("videodb://2/2/", filter, items); } void CVideoDatabase::GetMusicVideosByArtist(const CStdString& strArtist, CFileItemList& items) @@ -4947,8 +4950,10 @@ bool CVideoDatabase::GetSeasonsNav(const CStdString& strBaseDir, CFileItemList& m_pDS->close(); } // now add any linked movies - CStdString where = PrepareSQL("join movielinktvshow on movielinktvshow.idMovie=movieview.idMovie where movielinktvshow.idShow %s", strIn.c_str()); - GetMoviesByWhere("videodb://1/2/", where, "", items); + Filter filter; + filter.join = PrepareSQL("join movielinktvshow on movielinktvshow.idMovie=movieview.idMovie"); + filter.where = PrepareSQL("WHERE movielinktvshow.idShow %s", strIn.c_str()); + GetMoviesByWhere("videodb://1/2/", filter, items); return true; } catch (...) @@ -4960,26 +4965,44 @@ bool CVideoDatabase::GetSeasonsNav(const CStdString& strBaseDir, CFileItemList& bool CVideoDatabase::GetMoviesNav(const CStdString& strBaseDir, CFileItemList& items, int idGenre, int idYear, int idActor, int idDirector, int idStudio, int idCountry, int idSet) { - CStdString where; + Filter filter; if (idGenre != -1) - where = PrepareSQL("join genrelinkmovie on genrelinkmovie.idMovie=movieview.idMovie where genrelinkmovie.idGenre=%i", idGenre); + { + filter.join = PrepareSQL("join genrelinkmovie on genrelinkmovie.idMovie=movieview.idMovie"); + filter.where = PrepareSQL("where genrelinkmovie.idGenre=%i", idGenre); + } else if (idCountry != -1) - where = PrepareSQL("join countrylinkmovie on countrylinkmovie.idMovie=movieview.idMovie where countrylinkmovie.idCountry=%i", idCountry); + { + filter.join = PrepareSQL("join countrylinkmovie on countrylinkmovie.idMovie=movieview.idMovie"); + filter.where = PrepareSQL("where countrylinkmovie.idCountry=%i", idCountry); + } else if (idStudio != -1) - where = PrepareSQL("join studiolinkmovie on studiolinkmovie.idMovie=movieview.idMovie where studiolinkmovie.idStudio=%i", idStudio); + { + filter.join = PrepareSQL("join studiolinkmovie on studiolinkmovie.idMovie=movieview.idMovie"); + filter.where = PrepareSQL("where studiolinkmovie.idStudio=%i", idStudio); + } else if (idDirector != -1) - where = PrepareSQL("join directorlinkmovie on directorlinkmovie.idMovie=movieview.idMovie where directorlinkmovie.idDirector=%i", idDirector); + { + filter.join = PrepareSQL("join directorlinkmovie on directorlinkmovie.idMovie=movieview.idMovie"); + filter.where = PrepareSQL("where directorlinkmovie.idDirector=%i", idDirector); + } else if (idYear !=-1) - where = PrepareSQL("where c%02d='%i'",VIDEODB_ID_YEAR,idYear); + filter.where = PrepareSQL("where c%02d='%i'",VIDEODB_ID_YEAR,idYear); else if (idActor != -1) - where = PrepareSQL("join actorlinkmovie on actorlinkmovie.idMovie=movieview.idMovie join actors on actors.idActor=actorlinkmovie.idActor where actors.idActor=%i",idActor); + { + filter.join = PrepareSQL("join actorlinkmovie on actorlinkmovie.idMovie=movieview.idMovie join actors on actors.idActor=actorlinkmovie.idActor"); + filter.where = PrepareSQL("where actors.idActor=%i",idActor); + } else if (idSet != -1) - where = PrepareSQL("join setlinkmovie on setlinkmovie.idMovie=movieview.idMovie where setlinkmovie.idSet=%u",idSet); + { + filter.join = PrepareSQL("join setlinkmovie on setlinkmovie.idMovie=movieview.idMovie"); + filter.where = PrepareSQL("where setlinkmovie.idSet=%u",idSet); + } - return GetMoviesByWhere(strBaseDir, where, "", items, idSet == -1); + return GetMoviesByWhere(strBaseDir, filter, items, idSet == -1); } -bool CVideoDatabase::GetMoviesByWhere(const CStdString& strBaseDir, const CStdString &where, const CStdString &order, CFileItemList& items, bool fetchSets) +bool CVideoDatabase::GetMoviesByWhere(const CStdString& strBaseDir, const Filter &filter, CFileItemList& items, bool fetchSets /* = false */) { try { @@ -4994,20 +5017,37 @@ bool CVideoDatabase::GetMoviesByWhere(const CStdString& strBaseDir, const CStdSt { // user wants sets (and we're not fetching a particular set node), so grab all sets that match this where clause first CStdString setsWhere; - if (where.size()) - setsWhere = " where movie.idMovie in (select movieview.idMovie from movieview " + where + ")"; + if (!filter.where.empty() || !filter.join.empty()) + { + setsWhere = "where movie.idMovie in (select movieview.idMovie from movieview "; + if (!filter.join.empty()) + setsWhere += filter.join; + if (!filter.where.empty()) + setsWhere += " " + filter.where; + setsWhere += ")"; + } GetSetsNav("videodb://1/7/", items, VIDEODB_CONTENT_MOVIES, setsWhere); CStdString movieSetsWhere = "movieview.idMovie NOT IN (SELECT idMovie FROM setlinkmovie s1 JOIN(SELECT idSet, COUNT(1) AS c FROM setlinkmovie GROUP BY idSet HAVING c>1) s2 ON s2.idSet=s1.idSet)"; - if (where.size()) - strSQL += where + PrepareSQL(" and " + movieSetsWhere); + if (!filter.join.empty()) + strSQL += filter.join; + if (!filter.where.empty()) + { + strSQL += " " + filter.where; + strSQL += PrepareSQL(" AND " + movieSetsWhere); + } else strSQL += PrepareSQL(" WHERE " + movieSetsWhere); } else - strSQL += where; + { + if (!filter.join.empty()) + strSQL += filter.join; + if (!filter.where.empty()) + strSQL += " " + filter.where; + } - if (order.size()) - strSQL += " " + order; + if (filter.order.size()) + strSQL += " " + filter.order; int iRowsFound = RunQuery(strSQL); if (iRowsFound <= 0) @@ -5044,22 +5084,34 @@ bool CVideoDatabase::GetMoviesByWhere(const CStdString& strBaseDir, const CStdSt bool CVideoDatabase::GetTvShowsNav(const CStdString& strBaseDir, CFileItemList& items, int idGenre, int idYear, int idActor, int idDirector, int idStudio) { - CStdString where; + Filter filter; if (idGenre != -1) - where = PrepareSQL("join genrelinktvshow on genrelinktvshow.idShow=tvshowview.idShow where genrelinktvshow.idGenre=%i ", idGenre); + { + filter.join = PrepareSQL("join genrelinktvshow on genrelinktvshow.idShow=tvshowview.idShow"); + filter.where = PrepareSQL("where genrelinktvshow.idGenre=%i ", idGenre); + } else if (idStudio != -1) - where = PrepareSQL("join studiolinktvshow on studiolinktvshow.idShow=tvshowview.idShow where studiolinktvshow.idStudio=%i", idStudio); + { + filter.join = PrepareSQL("join studiolinktvshow on studiolinktvshow.idShow=tvshowview.idShow"); + filter.where = PrepareSQL("where studiolinktvshow.idStudio=%i", idStudio); + } else if (idDirector != -1) - where = PrepareSQL("join directorlinktvshow on directorlinktvshow.idShow=tvshowview.idShow where directorlinktvshow.idDirector=%i", idDirector); + { + filter.join = PrepareSQL("join directorlinktvshow on directorlinktvshow.idShow=tvshowview.idShow"); + filter.where = PrepareSQL("where directorlinktvshow.idDirector=%i", idDirector); + } else if (idYear != -1) - where = PrepareSQL("where c%02d like '%%%i%%'", VIDEODB_ID_TV_PREMIERED,idYear); + filter.where = PrepareSQL("where c%02d like '%%%i%%'", VIDEODB_ID_TV_PREMIERED,idYear); else if (idActor != -1) - where = PrepareSQL("join actorlinktvshow on actorlinktvshow.idShow=tvshowview.idShow join actors on actors.idActor=actorlinktvshow.idActor where actors.idActor=%i",idActor); + { + filter.join = PrepareSQL("join actorlinktvshow on actorlinktvshow.idShow=tvshowview.idShow join actors on actors.idActor=actorlinktvshow.idActor"); + filter.where = PrepareSQL("where actors.idActor=%i",idActor); + } - return GetTvShowsByWhere(strBaseDir, where, items); + return GetTvShowsByWhere(strBaseDir, filter, items); } -bool CVideoDatabase::GetTvShowsByWhere(const CStdString& strBaseDir, const CStdString &where, CFileItemList& items) +bool CVideoDatabase::GetTvShowsByWhere(const CStdString& strBaseDir, const Filter &filter, CFileItemList& items) { try { @@ -5068,7 +5120,14 @@ bool CVideoDatabase::GetTvShowsByWhere(const CStdString& strBaseDir, const CStdS if (NULL == m_pDB.get()) return false; if (NULL == m_pDS.get()) return false; - int iRowsFound = RunQuery("SELECT * FROM tvshowview " + where); + CStdString strSQL = "SELECT * FROM tvshowview "; + if (!filter.join.empty()) + strSQL += filter.join; + if (!filter.where.empty()) + strSQL += " " + filter.where; + if (!filter.order.empty()) + strSQL += " " + filter.order; + int iRowsFound = RunQuery(strSQL); if (iRowsFound <= 0) return iRowsFound == 0; @@ -5103,9 +5162,7 @@ bool CVideoDatabase::GetTvShowsByWhere(const CStdString& strBaseDir, const CStdS m_pDS->next(); } - CStdString order(where); - bool maintainOrder = order.ToLower().Find("order by") != -1; - Stack(items, VIDEODB_CONTENT_TVSHOWS, maintainOrder); + Stack(items, VIDEODB_CONTENT_TVSHOWS, !filter.order.empty()); // cleanup m_pDS->close(); @@ -5296,50 +5353,64 @@ void CVideoDatabase::Stack(CFileItemList& items, VIDEODB_CONTENT_TYPE type, bool bool CVideoDatabase::GetEpisodesNav(const CStdString& strBaseDir, CFileItemList& items, int idGenre, int idYear, int idActor, int idDirector, int idShow, int idSeason) { - CStdString where, strIn; + Filter filter; + CStdString strIn; if (idShow != -1) { strIn = PrepareSQL("= %i", idShow); GetStackedTvShowList(idShow, strIn); if (idGenre != -1) - where = PrepareSQL("join genrelinktvshow on genrelinktvshow.idShow=episodeview.idShow where episodeview.idShow=%i and genrelinktvshow.idGenre=%i",idShow,idGenre); + { + filter.join = PrepareSQL("join genrelinktvshow on genrelinktvshow.idShow=episodeview.idShow"); + filter.where = PrepareSQL("where episodeview.idShow=%i and genrelinktvshow.idGenre=%i",idShow,idGenre); + } else if (idDirector != -1) - where = PrepareSQL("join directorlinktvshow on directorlinktvshow.idShow=episodeview.idShow where episodeview.idShow=%i and directorlinktvshow.idDirector=%i",idShow,idDirector); + { + filter.join = PrepareSQL("join directorlinktvshow on directorlinktvshow.idShow=episodeview.idShow"); + filter.where = PrepareSQL("where episodeview.idShow=%i and directorlinktvshow.idDirector=%i",idShow,idDirector); + } else if (idYear !=-1) - where = PrepareSQL("where idShow=%i and premiered like '%%%i%%'", idShow, idYear); + { + filter.where = PrepareSQL("where idShow=%i and premiered like '%%%i%%'", idShow, idYear); + } else if (idActor != -1) - where = PrepareSQL("join actorlinktvshow on actorlinktvshow.idShow=episodeview.idShow where episodeview.idShow=%i and actorlinktvshow.idActor=%i",idShow,idActor); + { + filter.join = PrepareSQL("join actorlinktvshow on actorlinktvshow.idShow=episodeview.idShow"); + filter.where = PrepareSQL("where episodeview.idShow=%i and actorlinktvshow.idActor=%i",idShow,idActor); + } else - where = PrepareSQL("where idShow %s",strIn.c_str()); + filter.where = PrepareSQL("where idShow %s",strIn.c_str()); if (idSeason != -1) { if (idSeason == 0) // season = 0 indicates a special - we grab all specials here (see below) - where += PrepareSQL(" and c%02d=%i",VIDEODB_ID_EPISODE_SEASON,idSeason); + filter.where += PrepareSQL(" and c%02d=%i",VIDEODB_ID_EPISODE_SEASON,idSeason); else - where += PrepareSQL(" and (c%02d=%i or (c%02d=0 and (c%02d=0 or c%02d=%i)))",VIDEODB_ID_EPISODE_SEASON,idSeason,VIDEODB_ID_EPISODE_SEASON, VIDEODB_ID_EPISODE_SORTSEASON, VIDEODB_ID_EPISODE_SORTSEASON,idSeason); + filter.where += PrepareSQL(" and (c%02d=%i or (c%02d=0 and (c%02d=0 or c%02d=%i)))",VIDEODB_ID_EPISODE_SEASON,idSeason,VIDEODB_ID_EPISODE_SEASON, VIDEODB_ID_EPISODE_SORTSEASON, VIDEODB_ID_EPISODE_SORTSEASON,idSeason); } } else if (idYear !=-1) - where=PrepareSQL("where premiered like '%%%i%%'", idYear); + filter.where = PrepareSQL("where premiered like '%%%i%%'", idYear); // we always append show, season + episode in GetEpisodesByWhere CStdString parent, grandParent; URIUtils::GetParentPath(strBaseDir,parent); URIUtils::GetParentPath(parent,grandParent); - bool ret = GetEpisodesByWhere(grandParent, where, items); + bool ret = GetEpisodesByWhere(grandParent, filter, items); if (idSeason == -1 && idShow != -1) { // add any linked movies - CStdString where = PrepareSQL("join movielinktvshow on movielinktvshow.idMovie=movieview.idMovie where movielinktvshow.idShow %s", strIn.c_str()); - GetMoviesByWhere("videodb://1/2/", where, "", items); + Filter filter; + filter.join = PrepareSQL("join movielinktvshow on movielinktvshow.idMovie=movieview.idMovie"); + filter.where = PrepareSQL("where movielinktvshow.idShow %s", strIn.c_str()); + GetMoviesByWhere("videodb://1/2/", filter, items); } return ret; } -bool CVideoDatabase::GetEpisodesByWhere(const CStdString& strBaseDir, const CStdString &where, CFileItemList& items, bool appendFullShowPath /* = true */) +bool CVideoDatabase::GetEpisodesByWhere(const CStdString& strBaseDir, const Filter &filter, CFileItemList& items, bool appendFullShowPath /* = true */) { try { @@ -5349,7 +5420,14 @@ bool CVideoDatabase::GetEpisodesByWhere(const CStdString& strBaseDir, const CStd if (NULL == m_pDB.get()) return false; if (NULL == m_pDS.get()) return false; - int iRowsFound = RunQuery("select * from episodeview " + where); + CStdString strSQL = "select * from episodeview "; + if (!filter.join.empty()) + strSQL += filter.join; + if (!filter.where.empty()) + strSQL += " " + filter.where; + if (!filter.order.empty()) + strSQL += " " + filter.order; + int iRowsFound = RunQuery(strSQL); if (iRowsFound <= 0) return iRowsFound == 0; @@ -5396,45 +5474,60 @@ bool CVideoDatabase::GetEpisodesByWhere(const CStdString& strBaseDir, const CStd bool CVideoDatabase::GetMusicVideosNav(const CStdString& strBaseDir, CFileItemList& items, int idGenre, int idYear, int idArtist, int idDirector, int idStudio, int idAlbum) { - CStdString where; + Filter filter; if (idGenre != -1) - where = PrepareSQL("join genrelinkmusicvideo on genrelinkmusicvideo.idMVideo=musicvideoview.idMVideo where genrelinkmusicvideo.idGenre=%i", idGenre); + { + filter.join = PrepareSQL("join genrelinkmusicvideo on genrelinkmusicvideo.idMVideo=musicvideoview.idMVideo"); + filter.where = PrepareSQL("where genrelinkmusicvideo.idGenre=%i", idGenre); + } else if (idStudio != -1) - where = PrepareSQL("join studiolinkmusicvideo on studiolinkmusicvideo.idMVideo=musicvideoview.idMVideo where studiolinkmusicvideo.idStudio=%i", idStudio); + { + filter.join = PrepareSQL("join studiolinkmusicvideo on studiolinkmusicvideo.idMVideo=musicvideoview.idMVideo"); + filter.where = PrepareSQL("where studiolinkmusicvideo.idStudio=%i", idStudio); + } else if (idDirector != -1) - where = PrepareSQL("join directorlinkmusicvideo on directorlinkmusicvideo.idMVideo=musicvideoview.idMVideo where directorlinkmusicvideo.idDirector=%i", idDirector); + { + filter.join = PrepareSQL("join directorlinkmusicvideo on directorlinkmusicvideo.idMVideo=musicvideoview.idMVideo"); + filter.where = PrepareSQL("where directorlinkmusicvideo.idDirector=%i", idDirector); + } else if (idYear !=-1) - where = PrepareSQL("where c%02d='%i'",VIDEODB_ID_MUSICVIDEO_YEAR,idYear); + filter.where = PrepareSQL("where c%02d='%i'",VIDEODB_ID_MUSICVIDEO_YEAR,idYear); else if (idArtist != -1) - where = PrepareSQL("join artistlinkmusicvideo on artistlinkmusicvideo.idMVideo=musicvideoview.idMVideo join actors on actors.idActor=artistlinkmusicvideo.idArtist where actors.idActor=%i",idArtist); + { + filter.join = PrepareSQL("join artistlinkmusicvideo on artistlinkmusicvideo.idMVideo=musicvideoview.idMVideo join actors on actors.idActor=artistlinkmusicvideo.idArtist"); + filter.where = PrepareSQL("where actors.idActor=%i",idArtist); + } if (idAlbum != -1) { - CStdString str2 = PrepareSQL(" musicvideoview.c%02d=(select c%02d from musicvideo where idMVideo=%i)",VIDEODB_ID_MUSICVIDEO_ALBUM,VIDEODB_ID_MUSICVIDEO_ALBUM,idAlbum); - if (where.IsEmpty()) - where.Format(" %s%s","where",str2.c_str()); + CStdString str2 = PrepareSQL("musicvideoview.c%02d=(select c%02d from musicvideo where idMVideo=%i)",VIDEODB_ID_MUSICVIDEO_ALBUM,VIDEODB_ID_MUSICVIDEO_ALBUM,idAlbum); + if (filter.where.empty()) + filter.where = "where " + str2; else - where.Format(" %s %s%s",where.Mid(0).c_str(),"and",str2.c_str()); + filter.where += " and " + str2; } - return GetMusicVideosByWhere(strBaseDir, where, items); + return GetMusicVideosByWhere(strBaseDir, filter, items); } bool CVideoDatabase::GetRecentlyAddedMoviesNav(const CStdString& strBaseDir, CFileItemList& items, unsigned int limit) { - CStdString order = PrepareSQL("order by dateAdded desc, idMovie desc limit %u", limit ? limit : g_advancedSettings.m_iVideoLibraryRecentlyAddedItems); - return GetMoviesByWhere(strBaseDir, "", order, items); + Filter filter; + filter.order = PrepareSQL("order by dateAdded desc, idMovie desc limit %u", limit ? limit : g_advancedSettings.m_iVideoLibraryRecentlyAddedItems); + return GetMoviesByWhere(strBaseDir, filter, items); } bool CVideoDatabase::GetRecentlyAddedEpisodesNav(const CStdString& strBaseDir, CFileItemList& items, unsigned int limit) { - CStdString where = PrepareSQL("order by dateAdded desc, idEpisode desc limit %u", limit ? limit : g_advancedSettings.m_iVideoLibraryRecentlyAddedItems); - return GetEpisodesByWhere(strBaseDir, where, items, false); + Filter filter; + filter.order = PrepareSQL("order by dateAdded desc, idEpisode desc limit %u", limit ? limit : g_advancedSettings.m_iVideoLibraryRecentlyAddedItems); + return GetEpisodesByWhere(strBaseDir, filter, items, false); } bool CVideoDatabase::GetRecentlyAddedMusicVideosNav(const CStdString& strBaseDir, CFileItemList& items, unsigned int limit) { - CStdString where = PrepareSQL("order by dateAdded desc, idMVideo desc limit %u", limit ? limit : g_advancedSettings.m_iVideoLibraryRecentlyAddedItems); - return GetMusicVideosByWhere(strBaseDir, where, items); + Filter filter; + filter.order = PrepareSQL("order by dateAdded desc, idMVideo desc limit %u", limit ? limit : g_advancedSettings.m_iVideoLibraryRecentlyAddedItems); + return GetMusicVideosByWhere(strBaseDir, filter, items); } CStdString CVideoDatabase::GetGenreById(int id) @@ -6144,7 +6237,7 @@ void CVideoDatabase::GetMusicVideosByAlbum(const CStdString& strSearch, CFileIte } } -bool CVideoDatabase::GetMusicVideosByWhere(const CStdString &baseDir, const CStdString &whereClause, CFileItemList &items, bool checkLocks /*= true*/) +bool CVideoDatabase::GetMusicVideosByWhere(const CStdString &baseDir, const Filter &filter, CFileItemList &items, bool checkLocks /*= true*/) { try { @@ -6156,7 +6249,13 @@ bool CVideoDatabase::GetMusicVideosByWhere(const CStdString &baseDir, const CStd if (NULL == m_pDS.get()) return false; // We don't use PrepareSQL here, as the WHERE clause is already formatted. - CStdString strSQL = "select * from musicvideoview " + whereClause; + CStdString strSQL = "select * from musicvideoview "; + if (!filter.join.empty()) + strSQL += filter.join; + if (!filter.where.empty()) + strSQL += " " + filter.where; + if (!filter.order.empty()) + strSQL += " " + filter.order; CLog::Log(LOGDEBUG, "%s query = %s", __FUNCTION__, strSQL.c_str()); // run query @@ -6198,7 +6297,7 @@ bool CVideoDatabase::GetMusicVideosByWhere(const CStdString &baseDir, const CStd } catch (...) { - CLog::Log(LOGERROR, "%s (%s) failed", __FUNCTION__, whereClause.c_str()); + CLog::Log(LOGERROR, "%s failed", __FUNCTION__); } return false; } @@ -6453,8 +6552,8 @@ void CVideoDatabase::GetMusicVideosByName(const CStdString& strSearch, CFileItem { // Alternative searching - not quite as fast though due to // retrieving all information -// CStdString where = PrepareSQL("where c%02d like '%s%%' or c%02d like '%% %s%%'", VIDEODB_ID_MUSICVIDEO_TITLE, strSearch.c_str(), VIDEODB_ID_MUSICVIDEO_TITLE, strSearch.c_str()); -// GetMusicVideosByWhere("videodb://3/2/", where, items); +// Filter filter(PrepareSQL("where c%02d like '%s%%' or c%02d like '%% %s%%'", VIDEODB_ID_MUSICVIDEO_TITLE, strSearch.c_str(), VIDEODB_ID_MUSICVIDEO_TITLE, strSearch.c_str())); +// GetMusicVideosByWhere("videodb://3/2/", filter, items); CStdString strSQL; try @@ -6498,9 +6597,10 @@ void CVideoDatabase::GetEpisodesByPlot(const CStdString& strSearch, CFileItemLis { // Alternative searching - not quite as fast though due to // retrieving all information -// CStdString where = PrepareSQL("where c%02d like '%s%%' or c%02d like '%% %s%%'", VIDEODB_ID_EPISODE_PLOT, strSearch.c_str(), VIDEODB_ID_EPISODE_PLOT, strSearch.c_str()); -// where += PrepareSQL("or c%02d like '%s%%' or c%02d like '%% %s%%'", VIDEODB_ID_EPISODE_TITLE, strSearch.c_str(), VIDEODB_ID_EPISODE_TITLE, strSearch.c_str()); -// GetEpisodesByWhere("videodb://2/2/", where, items); +// Filter filter; +// filter.where = PrepareSQL("where c%02d like '%s%%' or c%02d like '%% %s%%'", VIDEODB_ID_EPISODE_PLOT, strSearch.c_str(), VIDEODB_ID_EPISODE_PLOT, strSearch.c_str()); +// filter.where += PrepareSQL("or c%02d like '%s%%' or c%02d like '%% %s%%'", VIDEODB_ID_EPISODE_TITLE, strSearch.c_str(), VIDEODB_ID_EPISODE_TITLE, strSearch.c_str()); +// GetEpisodesByWhere("videodb://2/2/", filter, items); // return; CStdString strSQL; @@ -7129,8 +7229,8 @@ void CVideoDatabase::DumpToDummyFiles(const CStdString &path) if (CDirectory::Create(TVFolder)) { // right - grab the episodes and dump them as well CFileItemList episodes; - CStdString where = PrepareSQL("where idShow=%i", items[i]->GetVideoInfoTag()->m_iDbId); - GetEpisodesByWhere("videodb://2/2/", where, episodes); + Filter filter(PrepareSQL("where idShow=%i", items[i]->GetVideoInfoTag()->m_iDbId)); + GetEpisodesByWhere("videodb://2/2/", filter, episodes); for (int i = 0; i < episodes.Size(); i++) { CVideoInfoTag *tag = episodes[i]->GetVideoInfoTag(); @@ -7147,7 +7247,7 @@ void CVideoDatabase::DumpToDummyFiles(const CStdString &path) } // get all movies items.Clear(); - GetMoviesByWhere("videodb://1/2/", "", "", items); + GetMoviesByWhere("videodb://1/2/", "", items); CStdString moviePath = URIUtils::AddFileToFolder(path, "movies"); CDirectory::Create(moviePath); for (int i = 0; i < items.Size(); i++) @@ -8098,23 +8198,23 @@ bool CVideoDatabase::GetItemsForPath(const CStdString &content, const CStdString if (content == "movies") { - CStdString where = PrepareSQL("where c%02d=%d", VIDEODB_ID_PARENTPATHID, pathID); - GetMoviesByWhere("", where, "", items); + Filter filter(PrepareSQL("where c%02d=%d", VIDEODB_ID_PARENTPATHID, pathID)); + GetMoviesByWhere("", filter, items); } else if (content == "episodes") { - CStdString where = PrepareSQL("where c%02d=%d", VIDEODB_ID_EPISODE_PARENTPATHID, pathID); - GetEpisodesByWhere("", where, items); + Filter filter(PrepareSQL("where c%02d=%d", VIDEODB_ID_EPISODE_PARENTPATHID, pathID)); + GetEpisodesByWhere("", filter, items); } else if (content == "tvshows") { - CStdString where = PrepareSQL("where c%02d=%d", VIDEODB_ID_TV_PARENTPATHID, pathID); - GetTvShowsByWhere("", where, items); + Filter filter(PrepareSQL("where c%02d=%d", VIDEODB_ID_TV_PARENTPATHID, pathID)); + GetTvShowsByWhere("", filter, items); } else if (content == "musicvideos") { - CStdString where = PrepareSQL("where c%02d=%d", VIDEODB_ID_MUSICVIDEO_PARENTPATHID, pathID); - GetMusicVideosByWhere("", where, items); + Filter filter(PrepareSQL("where c%02d=%d", VIDEODB_ID_MUSICVIDEO_PARENTPATHID, pathID)); + GetMusicVideosByWhere("", filter, items); } for (int i = 0; i < items.Size(); i++) items[i]->SetPath(items[i]->GetVideoInfoTag()->m_basePath); diff --git a/xbmc/video/VideoDatabase.h b/xbmc/video/VideoDatabase.h index 284cf91832..6aa888e1b4 100644 --- a/xbmc/video/VideoDatabase.h +++ b/xbmc/video/VideoDatabase.h @@ -309,6 +309,17 @@ class CVideoDatabase : public CDatabase { public: + class Filter + { + public: + Filter() {}; + Filter(const char *w) : where(w) {}; + Filter(const std::string &w) : where(w) {}; + std::string join; + std::string where; + std::string order; + }; + class CActor // used for actor retrieval for non-master users { public: @@ -611,10 +622,10 @@ public: bool ImportArtFromXML(const TiXmlNode *node, std::map<std::string, std::string> &artwork); // smart playlists and main retrieval work in these functions - bool GetMoviesByWhere(const CStdString& strBaseDir, const CStdString &where, const CStdString &order, CFileItemList& items, bool fetchSets = false); - bool GetTvShowsByWhere(const CStdString& strBaseDir, const CStdString &where, CFileItemList& items); - bool GetEpisodesByWhere(const CStdString& strBaseDir, const CStdString &where, CFileItemList& items, bool appendFullShowPath = true); - bool GetMusicVideosByWhere(const CStdString &baseDir, const CStdString &whereClause, CFileItemList& items, bool checkLocks = true); + bool GetMoviesByWhere(const CStdString& strBaseDir, const Filter &filter, CFileItemList& items, bool fetchSets = false); + bool GetTvShowsByWhere(const CStdString& strBaseDir, const Filter &filter, CFileItemList& items); + bool GetEpisodesByWhere(const CStdString& strBaseDir, const Filter &filter, CFileItemList& items, bool appendFullShowPath = true); + bool GetMusicVideosByWhere(const CStdString &baseDir, const Filter &filter, CFileItemList& items, bool checkLocks = true); // partymode int GetMusicVideoCount(const CStdString& strWhere); |