-//\r
-// Open Service Platform\r
-// Copyright (c) 2012 Samsung Electronics Co., Ltd.\r
-//\r
-// Licensed under the Apache License, Version 2.0 (the License);\r
-// you may not use this file except in compliance with the License.\r
-// You may obtain a copy of the License at\r
-//\r
-// http://www.apache.org/licenses/LICENSE-2.0\r
-//\r
-// Unless required by applicable law or agreed to in writing, software\r
-// distributed under the License is distributed on an "AS IS" BASIS,\r
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r
-// See the License for the specific language governing permissions and\r
-// limitations under the License.\r
-//\r
-/**\r
- * @file FCnt_ContentSearchImpl.cpp\r
- * @brief This is the implementation file for the %_ContentSearchImpl class.\r
- *\r
- * This file contains implementation of the %_ContentSearchImpl class.\r
- */\r
-\r
-#include <time.h>\r
-#include <FBaseSysLog.h>\r
-#include <FBaseInteger.h>\r
-#include <FBaseLongLong.h>\r
-#include <FBaseFloat.h>\r
-#include <FBaseColIList.h>\r
-#include <FBaseUtilStringTokenizer.h>\r
-#include <FCntContentSearch.h>\r
-#include <FCntContentSearchResult.h>\r
-#include <FBase_StringConverter.h>\r
-#include <FCnt_ContentUtility.h>\r
-#include <FCnt_ContentSearchImpl.h>\r
-\r
-using namespace Tizen::Base;\r
-using namespace Tizen::Base::Collection;\r
-using namespace Tizen::Base::Utility;\r
-using namespace Tizen::Io;\r
-\r
-namespace Tizen { namespace Content\r
-{\r
-\r
-static const int QUERY_LENGTH = 4096;\r
-\r
-// Declaration for Callback function registered to each media info details\r
-bool MediaItemCb(media_info_h media, void* pUserdata);\r
-// Declaration for Callback function registered to each column details\r
-bool GroupItemCb(const char* pGroupName, void* pUserdata);\r
-// Declaration for Callback function registered to each album details\r
-bool AlbumItemCb(media_album_h album, void* pUserdata);\r
-\r
-// Default constructor\r
-_ContentSearchImpl::_ContentSearchImpl(void)\r
- : Object()\r
- , __contentType(CONTENT_TYPE_UNKNOWN)\r
- , __pFinalOutList(NULL)\r
- , __inputExpr(L"")\r
- , __inputColumnName(L"")\r
- , __inputSortOrder(SORT_ORDER_NONE)\r
- , __pFilterHandle(0)\r
-{\r
- SysLog(NID_CNT, "Enter\n");\r
-}\r
-\r
-\r
-// Default destructor (disconnects the DB connection)\r
-_ContentSearchImpl::~_ContentSearchImpl(void)\r
-{\r
- SysLog(NID_CNT, "Enter\n");\r
-\r
- int ret = MEDIA_CONTENT_ERROR_NONE;\r
- result r = E_SUCCESS;\r
-\r
- ret = media_content_disconnect();\r
- r = MapCoreErrorToNativeResult(ret);\r
- SysTryLog(NID_CNT, r == E_SUCCESS, "[%s] Propagated in ~_ContentSearchImpl", GetErrorMessage(r));\r
-}\r
-\r
- _ContentSearchImpl*\r
- _ContentSearchImpl::GetInstance(ContentSearch& contentSearch)\r
-{\r
- return contentSearch.__pImpl;\r
-}\r
-\r
-const _ContentSearchImpl*\r
-_ContentSearchImpl::GetInstance(const ContentSearch& contentSearch)\r
-{\r
- return contentSearch.__pImpl;\r
-}\r
-\r
-//make a connection to DB\r
-result\r
-_ContentSearchImpl::Construct(ContentType type)\r
-{\r
- SysLog(NID_CNT, "Enter\n");\r
-\r
- result r = E_SUCCESS;\r
- int ret = MEDIA_CONTENT_ERROR_NONE;\r
-\r
- ret = media_content_connect();\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS , E_SYSTEM, "Failed to perform media_content_connect operation.");\r
-\r
- __contentType = type;\r
-\r
- return r;\r
-}\r
-\r
-// Creates a filter for the input query string along with content type\r
-// Initializes filter handle\r
-// Image - MEDIA_TYPE=0\r
-// Vide0 - MEDIA_TYPE=1\r
-// Audio - MEDIA_TYPE=2 or MEDIA_TYPE=3\r
-// Others - MEDIA_TYPE=4\r
-// All - none\r
-// Appends MEDIA_TYPE with "AND" (if the input expression is not empty and content type is not ALL) and input expression\r
-// Sets the condition and order.\r
-// If any argument is not proper E_INVALID_ARG is returned\r
-result\r
-_ContentSearchImpl::CreateQueryFilter(bool isAndAppendReq) const\r
-{\r
- int ret = MEDIA_CONTENT_ERROR_NONE;\r
- result r = E_SUCCESS;\r
-\r
- std::unique_ptr<char[]> pInputCond;\r
- std::unique_ptr<char[]> pSortCol;\r
-\r
- String inputCondition;\r
- String slpColumn;\r
-\r
- std::unique_ptr<filter_h, SearchFilterHandleDeleter> pFilterHandle(new (std::nothrow) filter_h);\r
-\r
- ret = media_filter_create(pFilterHandle.get());\r
- SysTryReturnResult(NID_CNT, ret == MEDIA_CONTENT_ERROR_NONE, E_SYSTEM, "Failed to perform media_filter_create operation.");\r
-\r
- switch (__contentType)\r
- {\r
- // Image-0,video-1,sound-2,music-3,other-4\r
- case CONTENT_TYPE_OTHER:\r
- inputCondition = "MEDIA_TYPE=4 ";\r
- break;\r
- case CONTENT_TYPE_IMAGE:\r
- inputCondition = "MEDIA_TYPE=0 ";\r
- break;\r
- case CONTENT_TYPE_AUDIO:\r
- inputCondition = "(MEDIA_TYPE=2 or MEDIA_TYPE=3) ";\r
- break;\r
- case CONTENT_TYPE_VIDEO:\r
- inputCondition = "MEDIA_TYPE=1 ";\r
- break;\r
- case CONTENT_TYPE_ALL:\r
- //If content type is CONTENT_TYPE_ALL, then MEDIA_TYPE is empty\r
- break;\r
- default:\r
- break;\r
- }\r
-\r
- if (!__inputExpr.IsEmpty())\r
- {\r
- if (isAndAppendReq && (!inputCondition.IsEmpty())) //For CONTENT_TYPE_ALL inputCondition is empty\r
- {\r
- r = inputCondition.Append("AND ");\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform append operation.");\r
- }\r
-\r
- r = inputCondition.Append(__inputExpr);\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform append operation.");\r
- }\r
-\r
- if (!inputCondition.IsEmpty())\r
- {\r
- //CopyToCharArrayN: utility function, converts a osp string to char*\r
- pInputCond = std::unique_ptr<char[]>(_StringConverter::CopyToCharArrayN(inputCondition));\r
- SysTryReturnResult(NID_CNT, pInputCond, E_OUT_OF_MEMORY, "pInputCond is NULL.");\r
-\r
- SysLog(NID_CNT, "pInputCond = %s", pInputCond.get());\r
-\r
- ret = media_filter_set_condition(*(pFilterHandle.get()), pInputCond.get(), MEDIA_CONTENT_COLLATE_DEFAULT);\r
- SysTryReturnResult(NID_CNT, ret == MEDIA_CONTENT_ERROR_NONE, E_SYSTEM, "Failed to perform media_filter_set_condition operation.");\r
- }\r
-\r
- if (!__inputColumnName.IsEmpty()) // SortColumn is optional in case of SearchN\r
- {\r
- //__inputColumnName (osp column name) is replaced with slpColumn (slp column name).\r
- r = GetSlpColumnName(slpColumn);\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform GetSlpColumnName operation.");\r
-\r
- //CopyToCharArrayN: utility function, converts a osp string to char*\r
-\r
- pSortCol = std::unique_ptr<char[]>(_StringConverter::CopyToCharArrayN(slpColumn));\r
- SysTryReturnResult(NID_CNT, pSortCol, E_OUT_OF_MEMORY, "pSortCol is NULL.");\r
-\r
- if (__inputSortOrder == SORT_ORDER_ASCENDING)\r
- {\r
- ret = media_filter_set_order(*(pFilterHandle.get()), MEDIA_CONTENT_ORDER_ASC, pSortCol.get(), MEDIA_CONTENT_COLLATE_DEFAULT);\r
- SysTryReturnResult(NID_CNT, ret == MEDIA_CONTENT_ERROR_NONE, E_SYSTEM, "Failed to perform media_filter_set_order operation.");\r
- }\r
- else if (__inputSortOrder == SORT_ORDER_DESCENDING)\r
- {\r
- ret = media_filter_set_order(*(pFilterHandle.get()), MEDIA_CONTENT_ORDER_DESC, pSortCol.get(), MEDIA_CONTENT_COLLATE_DEFAULT);\r
- SysTryReturnResult(NID_CNT, ret == MEDIA_CONTENT_ERROR_NONE, E_SYSTEM, "Failed to perform media_filter_set_order operation.");\r
- }\r
- }\r
-\r
- __pFilterHandle.reset(pFilterHandle.release());\r
-\r
- return r;\r
-}\r
-\r
-// Osp column names are mapped with slp column names\r
-// CONTENT_TYPE_OTHER and CONTENT_TYPE_IMAGE (0 - 13 ) are valid columns\r
-// CONTENT_TYPE_VIDEO (0 - 16 ) are valid columns\r
-// CONTENT_TYPE_ALL and CONTENT_TYPE_VIDEO (0 - 18 ) are valid columns\r
-// if the given osp column is out of the specified range of the type, E_INVALID_ARG is retuned.\r
-result\r
-_ContentSearchImpl::GetSlpColumnName(String& inputCol) const\r
-{\r
- String ospColumnName(L"");\r
- String slpColumnName(L"");\r
- String columnName(__inputColumnName);\r
- result r = E_SUCCESS;\r
- int maxCols = 0;\r
- switch (__contentType)\r
- {\r
- case CONTENT_TYPE_OTHER:\r
- //fall through\r
- case CONTENT_TYPE_IMAGE:\r
- maxCols = MAX_QUERY_COLUMNS_FOR_IMAGE_OTHERS;\r
- break;\r
- case CONTENT_TYPE_VIDEO:\r
- maxCols = MAX_QUERY_COLUMNS_FOR_VIDEO;\r
- break;\r
- case CONTENT_TYPE_AUDIO:\r
- //fall through\r
- case CONTENT_TYPE_ALL:\r
- maxCols = MAX_QUERY_COLUMNS;\r
- break;\r
- default:\r
- break;\r
- }\r
- for (int colIndex = 0; colIndex < maxCols; colIndex++)\r
- {\r
- ospColumnName.Clear();\r
- slpColumnName.Clear();\r
-\r
- ospColumnName = dbfieldinfo[colIndex].dbFieldOspName ;\r
- slpColumnName = dbfieldinfo[colIndex].dbFieldSlpName ;\r
-\r
- ospColumnName.ToUpper();\r
- columnName.ToUpper();\r
- if (columnName == ospColumnName)\r
- {\r
- inputCol = slpColumnName;\r
- return r;\r
- }\r
- }\r
- return E_INVALID_ARG;\r
-}\r
-\r
-//If the input expression contains any osp column name, it will be replaced with slp column name.\r
-// only CONTENT_TYPE_AUDIO and CONTENT_TYPE_ALL allowed to use all given columns\r
-// so, check for invalid column for CONTENT_TYPE_OTHER,CONTENT_TYPE_IMAGE and CONTENT_TYPE_VIDEO.\r
-// all the osp columns in the expression should be replaced with slp column names.\r
-// ' is used as a delimeter in parsing user query. so, \\' is saved as a special@apostrophe string.\r
-// \\' is replaced with '', which considers ' as normal character.\r
-\r
-result\r
-_ContentSearchImpl::ReplaceOspColumnNameWithSlp(void) const\r
-{\r
- String ospColumnName(L"");\r
- String slpColumnName(L"");\r
- String splApostrophe(L"special@apostrophe");\r
- result r = E_SUCCESS;\r
- int maxCols = 0;\r
-\r
- int indexOf = 0;\r
- \r
- String strToBeReplaced(L"\\'");\r
- int strLen = strToBeReplaced.GetLength();\r
- int startIndex = 0;\r
-\r
- while(E_SUCCESS == __inputExpr.IndexOf(strToBeReplaced,startIndex,indexOf))\r
- {\r
- int lenAfterSubStr = indexOf + strLen;\r
- while ((lenAfterSubStr < __inputExpr.GetLength()) && (__inputExpr[lenAfterSubStr] == ' '))\r
- {\r
- lenAfterSubStr++;\r
- }\r
- if ((lenAfterSubStr < __inputExpr.GetLength()) && ((__inputExpr[lenAfterSubStr] == '\'') ||\r
- ((!__inputExpr.StartsWith(L"AND ", lenAfterSubStr)) && (!__inputExpr.StartsWith(L"OR ", lenAfterSubStr)))))\r
- {\r
- r = __inputExpr.Remove(indexOf,strLen);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "Failed to perform Remove operation.");\r
- r = __inputExpr.Insert(splApostrophe,indexOf);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "Failed to perform Insert operation.");\r
- startIndex = indexOf + splApostrophe.GetLength();\r
- }\r
- else\r
- {\r
- startIndex = lenAfterSubStr;\r
- }\r
- }\r
-\r
- SysLog(NID_CNT, "__inputExpr after splApostrophe append = %ls", __inputExpr.GetPointer());\r
-\r
- switch (__contentType)\r
- {\r
- case CONTENT_TYPE_OTHER:\r
- //fall through\r
- case CONTENT_TYPE_IMAGE:\r
- r = CheckInvalidColumnInQuery();\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_INVALID_ARG, "Invalid Column In QueryString.");\r
- maxCols = MAX_QUERY_COLUMNS_FOR_IMAGE_OTHERS;\r
- break;\r
- case CONTENT_TYPE_VIDEO:\r
- r = CheckInvalidColumnInQuery();\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_INVALID_ARG, "Invalid Column In QueryString.");\r
- maxCols = MAX_QUERY_COLUMNS_FOR_VIDEO;\r
- break;\r
- case CONTENT_TYPE_AUDIO:\r
- //fall through\r
- case CONTENT_TYPE_ALL:\r
- maxCols = MAX_QUERY_COLUMNS;\r
- break;\r
- default:\r
- break;\r
- }\r
- for (int colIndex = 0; colIndex < maxCols; colIndex++)\r
- {\r
- ospColumnName.Clear();\r
- slpColumnName.Clear();\r
-\r
- ospColumnName = dbfieldinfo[colIndex].dbFieldOspName ;\r
- slpColumnName = dbfieldinfo[colIndex].dbFieldSlpName ;\r
-\r
- ReplaceString(ospColumnName,slpColumnName);\r
- }\r
-\r
- // Append ESCAPE '\' for LIKE query\r
- r = AppendEscapeKeywordForLikeQuery();\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "AppendEscapeKeywordForLikeQuery failed.");\r
-\r
- r = ReplaceDateTimeStringWithInt();\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_INVALID_ARG, "ReplaceDateTimeStringWithInt failed.");\r
-\r
- // replace splApostrophe string with actual\r
- r = __inputExpr.Replace(splApostrophe, "''");\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string Replace failed.");\r
-\r
- return r;\r
-}\r
-\r
-//This function is to appened ESCAPE keyword for _ and % special characters in LIKE query.\r
-\r
-result\r
-_ContentSearchImpl::AppendEscapeKeywordForLikeQuery(void) const\r
-{\r
- String delim = L"'"; //Delimeters is ' .\r
- result r = E_SUCCESS;\r
- bool isCol = true;\r
- bool isAppendEscape = false;\r
- String token;\r
- String tokenUpper;\r
- String inputExpr = __inputExpr;\r
-\r
- // Create a StringTokenizer instance\r
- StringTokenizer strTok(inputExpr, delim);\r
-\r
- inputExpr.Clear();\r
-\r
- while (strTok.HasMoreTokens())\r
- {\r
- r = strTok.GetNextToken(token);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "GetNextToken failed.");\r
- if (isCol) //column name\r
- {\r
- isCol = false;\r
- tokenUpper = token;\r
- tokenUpper.ToUpper();\r
- if (tokenUpper.Contains(" LIKE"))\r
- {\r
- isAppendEscape = true;\r
- }\r
- else\r
- {\r
- isAppendEscape = false;\r
- }\r
- r = inputExpr.Append(token);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");\r
- }\r
- else // value of the column\r
- {\r
- isCol = true;\r
- r = inputExpr.Append("'");\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");\r
- r = inputExpr.Append(token);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");\r
- r = inputExpr.Append("'");\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");\r
-\r
- if (isAppendEscape)\r
- {\r
- if (token.Contains("\\_") || token.Contains("\\%"))\r
- {\r
- r = inputExpr.Append("ESCAPE'\\' ");\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");\r
- }\r
- }\r
- }\r
- }\r
-\r
- __inputExpr.Clear();\r
- r = __inputExpr.Insert(inputExpr, 0);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string insert failed.");\r
-\r
- return r;\r
-}\r
-\r
-//This function is to replace DateTime value(osp datetime type is string) which is string with int.(SLP dateTime column type is int)\r
-\r
-result\r
-_ContentSearchImpl::ReplaceDateTimeStringWithInt(void) const\r
-{\r
- String delim = L"'"; //Delimeters is ' .\r
- result r = E_SUCCESS;\r
- bool isCol = true;\r
- bool isConvertReq = false;\r
- bool isBetweenExistsInDateTimeQuery = false;\r
- String token;\r
- String tokenUpper;\r
- String inputExpr = __inputExpr;\r
-\r
- if(!inputExpr.Contains("MEDIA_ADDED_TIME"))\r
- {\r
- return r;\r
- }\r
-\r
- // Create a StringTokenizer instance\r
- StringTokenizer strTok(inputExpr, delim);\r
-\r
- inputExpr.Clear();\r
-\r
- while (strTok.HasMoreTokens())\r
- {\r
- r = strTok.GetNextToken(token);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "GetNextToken failed.");\r
- if (isCol) //column name\r
- {\r
- isCol = false;\r
- tokenUpper = token;\r
- tokenUpper.ToUpper();\r
- if(isBetweenExistsInDateTimeQuery)\r
- {\r
- isBetweenExistsInDateTimeQuery = false;\r
- isConvertReq = true;\r
- }\r
- else\r
- {\r
- if (tokenUpper.Contains("MEDIA_ADDED_TIME"))\r
- {\r
- if (tokenUpper.Contains("BETWEEN"))\r
- {\r
- isBetweenExistsInDateTimeQuery = true;\r
- }\r
- isConvertReq = true;\r
- }\r
- else\r
- {\r
- isConvertReq = false;\r
- }\r
- }\r
-\r
- r = inputExpr.Append(token);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "string append failed.");\r
- }\r
- else // value of the column\r
- {\r
- isCol = true;\r
- r = inputExpr.Append("'");\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "string append failed.");\r
-\r
- if (isConvertReq)\r
- {\r
- Tizen::Base::DateTime dt;\r
- r = Tizen::Base::DateTime::Parse(token, dt);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "Failed to parse DateTime.");\r
-\r
- int year = dt.GetYear();\r
- int month = dt.GetMonth(); \r
- int day = dt.GetDay();\r
- int hour = dt.GetHour();\r
- int minute = dt.GetMinute(); \r
- int second = dt.GetSecond();\r
- \r
- time_t rawTime;\r
- struct tm* timeInfo;\r
-\r
- time(&rawTime);\r
- timeInfo = localtime(&rawTime);\r
- timeInfo->tm_year = year - 1900;\r
- timeInfo->tm_mon = month - 1;\r
- timeInfo->tm_mday = day;\r
- timeInfo->tm_hour = hour;\r
- timeInfo->tm_min = minute;\r
- timeInfo->tm_sec = second;\r
-\r
- time_t seconds = mktime(timeInfo);\r
- SysTryReturnResult(NID_CNT, seconds != -1, E_INVALID_ARG, "Failed to convert DateTime to broken-down time.");\r
-\r
- long long ticksInSeconds = (long long)seconds;\r
-\r
- r = inputExpr.Append(ticksInSeconds);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "string append failed.");\r
- }\r
- else\r
- {\r
- r = inputExpr.Append(token);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "string append failed.");\r
- }\r
-\r
- r = inputExpr.Append("'");\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "string append failed.");\r
- }\r
- }\r
-\r
- __inputExpr.Clear();\r
- r = __inputExpr.Insert(inputExpr, 0);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "string insert failed.");\r
-\r
- return r;\r
-}\r
-\r
-// CONTENT_TYPE_OTHER and CONTENT_TYPE_IMAGE (0 - 13 ) are valid columns\r
-// CONTENT_TYPE_VIDEO (0 - 16 ) are valid columns\r
-// CONTENT_TYPE_ALL and CONTENT_TYPE_VIDEO (0 - 18 ) are valid columns\r
-// This functions checks for invalid column in the given input string (only allowed columns should be used by content type other wise\r
-// E_INVALID_ARG is returned)\r
-// StringTokenizer is used to parse input expression, by using delimater "'", to differentiate column and value.\r
-// As values may also contain column names\r
-// Ex: 1. where author = syam_author_01 2. where album = jalsa_album_name_01.\r
-\r
-result\r
-_ContentSearchImpl::CheckInvalidColumnInQuery(void) const\r
-{\r
- result r = E_SUCCESS;\r
- int tokenNo = 0;\r
- String delim = L"'"; //Delimeters is ' .\r
- bool isColReplaceReq = true;\r
- String token;\r
- String inputExpr = __inputExpr;\r
-\r
- // Create a StringTokenizer instance\r
- StringTokenizer strTok(inputExpr, delim);\r
-\r
- inputExpr.Clear();\r
-\r
- while (strTok.HasMoreTokens())\r
- {\r
- r = strTok.GetNextToken(token);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "strTok GetNextToken failed.");\r
-\r
- SysLog(NID_CNT, "In CheckInvalidColumnInQuery token[%d] = %ls", ++tokenNo, token.GetPointer());\r
-\r
- if (isColReplaceReq)\r
- {\r
- isColReplaceReq = false;\r
- r = inputExpr.Append(token);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");\r
- token.ToUpper();\r
- switch (__contentType)\r
- {\r
- case CONTENT_TYPE_OTHER:\r
- //fall through\r
- case CONTENT_TYPE_IMAGE:\r
- if ((token.Contains("TITLE")) || (token.Contains("ARTIST")) || (token.Contains("GENRE")))\r
- {\r
- SysLog(NID_CNT, "Title or Artist or Genre are not valid cloumns for this content type");\r
- return E_INVALID_ARG;\r
- }\r
- //fall through\r
- case CONTENT_TYPE_VIDEO:\r
- if ((token.Contains("COMPOSER")) || (token.Contains("ALBUM")))\r
- {\r
- SysLog(NID_CNT, "Composer or Album are not valid cloumns for this content type");\r
- return E_INVALID_ARG;\r
- }\r
- break;\r
- default:\r
- break;\r
- }\r
- }\r
- else\r
- {\r
- isColReplaceReq = true;\r
- r = inputExpr.Append("'");\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");\r
- r = inputExpr.Append(token);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");\r
- r = inputExpr.Append("'");\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");\r
- }\r
- }\r
- return r;\r
-}\r
-\r
-// It replaces osp column name with slp column name.\r
-// StringTokenizer is used to parse input expression, by using delimater "'", to differentiate column and value.\r
-// As values may also contain column names\r
-// Only column names are replaced but not values(values may contain column names)\r
-// Ex: 1. where author = syam_author_01 2. where album = jalsa_album_name_01.\r
-\r
-result\r
-_ContentSearchImpl::ReplaceString(String ospColumnName, String slpColumnName) const\r
-{\r
- String delim = L"'"; //Delimeters is ' .\r
- result r = E_SUCCESS;\r
- bool isColReplaceReq = true;\r
- String token;\r
- String inputExpr = __inputExpr;\r
-\r
- // Create a StringTokenizer instance\r
- StringTokenizer strTok(inputExpr, delim);\r
-\r
- inputExpr.Clear();\r
-\r
- while (strTok.HasMoreTokens())\r
- {\r
- r = strTok.GetNextToken(token); // Osp, StringTokenizer, Sample, code\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string GetNextToken() failed.");\r
- if (isColReplaceReq) //column name\r
- {\r
- isColReplaceReq = false;\r
- r = token.Replace(ospColumnName, slpColumnName);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string replace() failed.");\r
- r = inputExpr.Append(token);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");\r
- }\r
- else // value of the column\r
- {\r
- isColReplaceReq = true;\r
- r = inputExpr.Append("'");\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");\r
- r = inputExpr.Append(token);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");\r
- r = inputExpr.Append("'");\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");\r
- }\r
- }\r
- __inputExpr.Clear();\r
- r = __inputExpr.Insert(inputExpr, 0);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string insert() failed.");\r
-\r
- return r;\r
-}\r
-\r
-//Retuns list of search result for the given expression and content type.\r
-Collection::IList*\r
-_ContentSearchImpl::SearchN(int pageNo, int countPerPage, int& totalPageCount, int& totalCount, const String& whereExpr, const String& sortColumn, SortOrder sortOrder) const\r
-{\r
- SysLog(NID_CNT, "pageNo = %d, countPerPage = %d, whereExpr = %ls", pageNo, countPerPage, whereExpr.GetPointer());\r
-\r
- ClearLastResult();\r
-\r
- result r = E_SUCCESS;\r
- int ret = MEDIA_CONTENT_ERROR_NONE;\r
- int offset = 0;\r
-\r
- __inputColumnName.Clear();\r
- __inputExpr.Clear();\r
- __inputColumnName = sortColumn;\r
- __inputSortOrder = sortOrder;\r
- totalPageCount = 0;\r
- totalCount = 0;\r
-\r
- if (!whereExpr.IsEmpty()) // copy whereExpr if not empty to class variable __inputExpr\r
- {\r
- //r = __inputExpr.Format(QUERY_LENGTH, L"%ls", whereExpr.GetPointer());\r
- r = __inputExpr.Append(whereExpr);\r
- SysTryReturn(NID_CNT, r == E_SUCCESS, NULL, r, "[%s] __inputExpr.Append Failed as whereExpr is not empty.", GetErrorMessage(r));\r
-\r
- r = ReplaceOspColumnNameWithSlp();\r
- SysTryReturn(NID_CNT, r == E_SUCCESS, NULL, r, "[%s] ReplaceOspColumnNameWithSlp for InputExpr Failed.", GetErrorMessage(r));\r
-\r
- SysLog(NID_CNT, "After replace __inputExpr = %ls", __inputExpr.GetPointer());\r
- }\r
- if ((__inputColumnName.IsEmpty()) && ((__inputSortOrder == SORT_ORDER_ASCENDING) || (__inputSortOrder == SORT_ORDER_DESCENDING)))\r
- {\r
- SysLog(NID_CNT, "sort column name is empty and sort oder is not none. so,E_INVALID_ARG occured.");\r
- SetLastResult(E_INVALID_ARG);\r
- return null;\r
- }\r
- else\r
- {\r
- std::unique_ptr<ArrayList, AllElementsDeleter> pFinalOutList(new (std::nothrow) ArrayList());\r
- SysTryReturn(NID_CNT, pFinalOutList.get() != null, NULL, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Failed to construct ArrayList.");\r
-\r
- r = pFinalOutList->Construct();\r
- SysTryReturn(NID_CNT, !IsFailed(r), NULL, r, "[%s] Failed to construct ArrayList.", GetErrorMessage(r));\r
-\r
- __pFinalOutList = std::move(pFinalOutList);\r
-\r
- r = CreateQueryFilter(true);\r
- SysTryReturn(NID_CNT, !IsFailed(r), NULL, r, "[%s] Failed to perform CreateQueryFilter operation.", GetErrorMessage(r));\r
-\r
- ret = media_info_get_media_count_from_db(*(__pFilterHandle.get()), &totalCount);\r
- r = MapCoreErrorToNativeResult(ret);\r
- SysTryReturn(NID_CNT, r == E_SUCCESS , NULL, r, "[%s] Failed to perform media_info_get_media_count_from_db operation.", GetErrorMessage(r));\r
-\r
- SysLog(NID_CNT, "totalCount is [%d] for media_info_get_media_count_from_db", totalCount);\r
-\r
- if (totalCount > 0)\r
- {\r
- if ((totalCount % countPerPage) == 0)\r
- {\r
- totalPageCount = totalCount / countPerPage;\r
- }\r
- else\r
- {\r
- totalPageCount = (totalCount / countPerPage) + 1;\r
- }\r
-\r
- SysTryReturn(NID_CNT, ((pageNo >= 1) && (pageNo <= totalPageCount)) , NULL, E_INVALID_ARG, "[E_INVALID_ARG] (pageNo < 1) || (pageNo > totalPageCount).");\r
-\r
- offset = (pageNo * countPerPage) - countPerPage;\r
-\r
- SysLog(NID_CNT, " SearchN totalCount [%d] totalPageCount[%d] __countPerPage[%d] __pageNo[%d] offset[%d]",\r
- totalCount, totalPageCount, countPerPage, pageNo, offset);\r
-\r
- ret = media_filter_set_offset(*(__pFilterHandle.get()), offset, countPerPage);\r
- r = MapCoreErrorToNativeResult(ret);\r
- SysTryReturn(NID_CNT, r == E_SUCCESS, NULL, r,\r
- "[%s] Failed to perform media_filter_set_offset operation.", GetErrorMessage(r));\r
-\r
- r = ExecuteAndFillFinalOutList();\r
- SysTryReturn(NID_CNT, r == E_SUCCESS, NULL, E_SYSTEM, "[E_SYSTEM] ExecuteAndFillFinalOutList Failed.");\r
- }\r
- else if (pageNo > 1)\r
- {\r
- r = E_INVALID_ARG;\r
- SysTryReturn(NID_CNT, r == E_SUCCESS, NULL, r, "[E_INVALID_ARG] (pageNo > 1) and (totalcount = 0).");\r
- }\r
- }\r
- SetLastResult(r);\r
- return __pFinalOutList.release();\r
-}\r
-\r
-// Fills final result list\r
-result\r
-_ContentSearchImpl::ExecuteAndFillFinalOutList(void) const\r
-{\r
- SysLog(NID_CNT, "Enter\n");\r
-\r
- int ret = MEDIA_CONTENT_ERROR_NONE;\r
- result r = E_SUCCESS;\r
-\r
- std::unique_ptr<GList, SearchGListDeleter> pItemList;\r
- GList* pTemp = NULL;\r
- std::unique_ptr<media_info_s, SearchMediaHandleDeleter> pMediaHandle;\r
-\r
- ContentInfo::_ContentData* pContentData = null;\r
- ImageContentInfo::_ImageContentData* pImageContentData = null;\r
- AudioContentInfo::_AudioContentData* pAudioContentData = null;\r
- VideoContentInfo::_VideoContentData* pVideoContentData = null;\r
-\r
- std::unique_ptr<ImageContentInfo> pImageContentInfo;\r
- std::unique_ptr<AudioContentInfo> pAudioContentInfo;\r
- std::unique_ptr<VideoContentInfo> pVideoContentInfo;\r
- std::unique_ptr<OtherContentInfo> pOtherContentInfo;\r
-\r
- std::unique_ptr<ContentSearchResult> pContentSearchResult;\r
-\r
- pTemp = pItemList.get();\r
-\r
- ret = media_info_foreach_media_from_db(*(__pFilterHandle.get()), MediaItemCb, &pTemp);\r
- r = MapCoreErrorToNativeResult(ret);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "Failed to perform media_info_foreach_media_from_db operation.");\r
-\r
- SysTryReturnResult(NID_CNT, pTemp != NULL, r, "media_info_foreach_media_from_db pTemp is null.");\r
-\r
- media_content_type_e mediaType = MEDIA_CONTENT_TYPE_OTHERS;\r
-\r
- for (int idx = 0; idx < (int)g_list_length(pTemp); idx++)\r
- {\r
- pMediaHandle.reset(static_cast<media_info_h>(g_list_nth_data(pTemp, idx)));\r
-\r
- ret = media_info_get_media_type(pMediaHandle.get(), &mediaType);\r
- r = MapCoreErrorToNativeResult(ret);\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform media_info_get_media_type.");\r
-\r
- switch (mediaType)\r
- {\r
- case MEDIA_CONTENT_TYPE_OTHERS:\r
- //memset(&contentData, 0, sizeof(contentData));\r
-\r
- pOtherContentInfo = std::unique_ptr<OtherContentInfo>(new (std::nothrow) OtherContentInfo);\r
- SysTryReturnResult(NID_CNT, pOtherContentInfo.get() != null, E_OUT_OF_MEMORY, "Failed to create pOtherContentInfo.");\r
-\r
- pContentData = pOtherContentInfo->GetContentData();\r
- SysTryReturnResult(NID_CNT, pContentData != null, E_OUT_OF_MEMORY, "The memory is insufficient.");\r
-\r
- r = _ContentUtility::FillContentData(pMediaHandle.get(), pContentData);\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform FillContentData operation.");\r
-\r
-\r
- pContentSearchResult = std::unique_ptr<ContentSearchResult>(new (std::nothrow) ContentSearchResult);\r
- SysTryReturnResult(NID_CNT, pContentSearchResult.get() != null, E_OUT_OF_MEMORY, "Failed to create pContentSearchResult.");\r
-\r
- pContentSearchResult->SetContentType(CONTENT_TYPE_OTHER);\r
- pContentSearchResult->SetContentInfo(pOtherContentInfo.release());\r
-\r
- // Shallow copy, adds just the pointer: not the element\r
-\r
- r = __pFinalOutList->Add(*(pContentSearchResult.release()));\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform Add operation for ArrayList.");\r
-\r
- //pOtherContentInfo = null;\r
- //pContentSearchResult = null;\r
- //_ContentUtility::DeleteContentData(&contentData);\r
- break;\r
- case MEDIA_CONTENT_TYPE_IMAGE:\r
- //memset(&contentData, 0, sizeof(contentData));\r
- //memset(&imageContentData, 0, sizeof(imageContentData));\r
-\r
- pImageContentInfo = std::unique_ptr<ImageContentInfo>(new (std::nothrow) ImageContentInfo);\r
- SysTryReturnResult(NID_CNT, pImageContentInfo.get() != null, E_OUT_OF_MEMORY, "Failed to create pImageContentInfo.");\r
-\r
- pContentData = pImageContentInfo->GetContentData();\r
- SysTryReturnResult(NID_CNT, pContentData != null, E_OUT_OF_MEMORY, "The memory is insufficient.");\r
-\r
- pImageContentData = pImageContentInfo->GetImageContentData();\r
- SysTryReturnResult(NID_CNT, pImageContentData != null, E_OUT_OF_MEMORY, "The memory is insufficient.");\r
-\r
- r = _ContentUtility::FillContentData(pMediaHandle.get(), pContentData);\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform FillContentData operation.");\r
-\r
- r = _ContentUtility::FillImageContentData(pMediaHandle.get(), pImageContentData);\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform GetDataFromImageTable operation.");\r
-\r
- pContentSearchResult = std::unique_ptr<ContentSearchResult>(new (std::nothrow) ContentSearchResult);\r
- SysTryReturnResult(NID_CNT, pContentSearchResult.get() != null, E_OUT_OF_MEMORY, "Failed to create pContentSearchResult.");\r
-\r
- pContentSearchResult->SetContentType(CONTENT_TYPE_IMAGE);\r
- pContentSearchResult->SetContentInfo(pImageContentInfo.release());\r
-\r
- // Shallow copy, adds just the pointer: not the element\r
-\r
- r = __pFinalOutList->Add(*(pContentSearchResult.release()));\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform Add operation for ArrayList.");\r
- //pImageContentInfo = null;\r
- //pContentSearchResult = null;\r
- //_ContentUtility::DeleteContentData(&contentData);\r
- break;\r
- case MEDIA_CONTENT_TYPE_MUSIC:\r
- //fall through\r
- case MEDIA_CONTENT_TYPE_SOUND:\r
- //memset(&contentData, 0, sizeof(contentData));\r
- //memset(&audioContentData, 0, sizeof(audioContentData));\r
-\r
- pAudioContentInfo = std::unique_ptr<AudioContentInfo>(new (std::nothrow) AudioContentInfo);\r
- SysTryReturnResult(NID_CNT, pAudioContentInfo.get() != null, E_OUT_OF_MEMORY, "Failed to create pAudioContentInfo.");\r
-\r
- pContentData = pAudioContentInfo->GetContentData();\r
- SysTryReturnResult(NID_CNT, pContentData != null, E_OUT_OF_MEMORY, "The memory is insufficient.");\r
-\r
- pAudioContentData = pAudioContentInfo->GetAudioContentData();\r
- SysTryReturnResult(NID_CNT, pAudioContentData != null, E_OUT_OF_MEMORY, "The memory is insufficient.");\r
-\r
- r = _ContentUtility::FillContentData(pMediaHandle.get(), pContentData);\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform FillContentData operation.");\r
-\r
- r = _ContentUtility::FillAudioContentData(pMediaHandle.get(), pAudioContentData);\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform FillAudioContentData operation.");\r
-\r
- pContentSearchResult = std::unique_ptr<ContentSearchResult>(new (std::nothrow) ContentSearchResult);\r
- SysTryReturnResult(NID_CNT, pContentSearchResult.get() != null, E_OUT_OF_MEMORY, "Failed to create pContentSearchResult.");\r
-\r
- pContentSearchResult->SetContentType(CONTENT_TYPE_AUDIO);\r
- pContentSearchResult->SetContentInfo(pAudioContentInfo.release());\r
-\r
- // Shallow copy, adds just the pointer: not the element\r
-\r
- r = __pFinalOutList->Add(*(pContentSearchResult.release()));\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform Add operation for ArrayList.");\r
-\r
- //pAudioContentInfo = null;\r
- //pContentSearchResult = null;\r
- //_ContentUtility::DeleteContentData(&contentData);\r
- //_ContentUtility::DeleteAudioContentData(&audioContentData);\r
- break;\r
- case MEDIA_CONTENT_TYPE_VIDEO:\r
- //memset(&contentData, 0, sizeof(contentData));\r
- //memset(&videoContentData, 0, sizeof(videoContentData));\r
-\r
- pVideoContentInfo = std::unique_ptr<VideoContentInfo>(new (std::nothrow) VideoContentInfo);\r
- SysTryReturnResult(NID_CNT, pVideoContentInfo.get() != null, E_OUT_OF_MEMORY, "Failed to create pVideoContentInfo.");\r
-\r
- pContentData = pVideoContentInfo->GetContentData();\r
- SysTryReturnResult(NID_CNT, pContentData != null, E_OUT_OF_MEMORY, "The memory is insufficient.");\r
-\r
- pVideoContentData = pVideoContentInfo->GetVideoContentData();\r
- SysTryReturnResult(NID_CNT, pVideoContentData != null, E_OUT_OF_MEMORY, "The memory is insufficient.");\r
-\r
- r = _ContentUtility::FillContentData(pMediaHandle.get(), pContentData);\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform FillContentData operation.");\r
-\r
- r = _ContentUtility::FillVideoContentData(pMediaHandle.get(), pVideoContentData);\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform FillVideoContentData operation.");\r
-\r
- pContentSearchResult = std::unique_ptr<ContentSearchResult>(new (std::nothrow) ContentSearchResult);\r
- SysTryReturnResult(NID_CNT, pContentSearchResult.get() != null, E_OUT_OF_MEMORY, "Failed to create pContentSearchResult.");\r
-\r
- pContentSearchResult->SetContentType(CONTENT_TYPE_VIDEO);\r
- pContentSearchResult->SetContentInfo(pVideoContentInfo.release());\r
-\r
- // Shallow copy, adds just the pointer: not the element\r
-\r
- r = __pFinalOutList->Add(*(pContentSearchResult.release()));\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform Add operation for ArrayList.");\r
-\r
- //pVideoContentInfo = null;\r
- //pContentSearchResult = null;\r
- //_ContentUtility::DeleteContentData(&contentData);\r
- //_ContentUtility::DeleteVideoContentData(&videoContentData);\r
- break;\r
- default:\r
- break;\r
- }\r
- }\r
- return r;\r
-}\r
-\r
-// returns given column value list in the requested order\r
-Collection::IList*\r
-_ContentSearchImpl::GetValueListN(const String& sortColumn, SortOrder sortOrder)\r
-{\r
- SysLog(NID_CNT, "inputColumn = %ls", sortColumn.GetPointer());\r
- ClearLastResult();\r
-\r
- result r = E_SUCCESS;\r
- int colIndex = 0;\r
- int maxCols = 0;\r
-\r
- __inputColumnName.Clear();\r
- __inputExpr.Clear();\r
-\r
- __inputColumnName = sortColumn;\r
- __inputSortOrder = sortOrder;\r
-\r
- String ospColumnName(L"");\r
- String slpColumnName(L"");\r
-\r
- String columnName(__inputColumnName);\r
-\r
- if ((__inputColumnName.IsEmpty()) && ((__inputSortOrder == SORT_ORDER_ASCENDING) || (__inputSortOrder == SORT_ORDER_DESCENDING)))\r
- {\r
- SysLog(NID_CNT, "sort column name is empty and sort oder is not none. so,E_INVALID_ARG occured.");\r
- SetLastResult(E_INVALID_ARG);\r
- return null;\r
- }\r
- else\r
- {\r
- std::unique_ptr<ArrayList, AllElementsDeleter> pFinalOutList(new (std::nothrow) ArrayList());\r
- SysTryReturn(NID_CNT, pFinalOutList.get() != null, NULL, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Failed to construct ArrayList.");\r
-\r
- r = pFinalOutList->Construct();\r
- SysTryReturn(NID_CNT, !IsFailed(r), NULL, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Failed to construct ArrayList.");\r
-\r
- __pFinalOutList = std::move(pFinalOutList);\r
-\r
- switch (__contentType)\r
- {\r
- case CONTENT_TYPE_OTHER:\r
- //fall through\r
- case CONTENT_TYPE_IMAGE:\r
- maxCols = MAX_QUERY_COLUMNS_FOR_IMAGE_OTHERS;\r
- break;\r
- case CONTENT_TYPE_VIDEO:\r
- maxCols = MAX_QUERY_COLUMNS_FOR_VIDEO;\r
- break;\r
- case CONTENT_TYPE_AUDIO:\r
- //fall through\r
- case CONTENT_TYPE_ALL:\r
- maxCols = MAX_QUERY_COLUMNS;\r
- break;\r
- default:\r
- break;\r
- }\r
-\r
- for (colIndex = 0; colIndex < maxCols; colIndex++)\r
- {\r
- ospColumnName.Clear();\r
- slpColumnName.Clear();\r
-\r
- ospColumnName = dbfieldinfo[colIndex].dbFieldOspName ;\r
- slpColumnName = dbfieldinfo[colIndex].dbFieldSlpName ;\r
-\r
- ospColumnName.ToUpper();\r
- columnName.ToUpper();\r
- if (columnName == ospColumnName)\r
- {\r
- r = FillColumnsList(colIndex);\r
- SysTryReturn(NID_CNT, r == E_SUCCESS, NULL, r, "[%s] FillColumnsList Failed.", GetErrorMessage(r));\r
- break;\r
- }\r
- }\r
- if (colIndex == maxCols)\r
- {\r
- r = E_INVALID_ARG;\r
- SysTryReturn(NID_CNT, r == E_SUCCESS, NULL, r, "[E_INVALID_ARG] invalid column.");\r
- }\r
- }\r
- SetLastResult(r);\r
- return __pFinalOutList.release();\r
-}\r
-\r
-// returns given column value list in the requested order\r
-Collection::IList*\r
-_ContentSearchImpl::GetValueListN(int pageNo, int countPerPage, int& totalPageCount, int& totalCount, const String& sortColumn, SortOrder sortOrder) const\r
-{\r
- SysLog(NID_CNT, "pageNo = %d, countPerPage = %d, inputColumn = %ls", pageNo, countPerPage, sortColumn.GetPointer());\r
-\r
- ClearLastResult();\r
-\r
- result r = E_SUCCESS;\r
- int colIndex = 0;\r
- int maxCols = 0;\r
-\r
- __inputColumnName.Clear();\r
- __inputExpr.Clear();\r
-\r
- __inputColumnName = sortColumn;\r
- __inputSortOrder = sortOrder;\r
-\r
- String ospColumnName(L"");\r
- String slpColumnName(L"");\r
-\r
- String columnName(__inputColumnName);\r
-\r
- if ((__inputColumnName.IsEmpty()) && ((__inputSortOrder == SORT_ORDER_ASCENDING) || (__inputSortOrder == SORT_ORDER_DESCENDING)))\r
- {\r
- SysLog(NID_CNT, "sort column name is empty and sort oder is not none. so,E_INVALID_ARG occured.");\r
- SetLastResult(E_INVALID_ARG);\r
- return null;\r
- }\r
- else\r
- {\r
- std::unique_ptr<ArrayList, AllElementsDeleter> pFinalOutList(new (std::nothrow) ArrayList());\r
- SysTryReturn(NID_CNT, pFinalOutList.get() != null, NULL, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Failed to construct ArrayList.");\r
-\r
- r = pFinalOutList->Construct();\r
- SysTryReturn(NID_CNT, !IsFailed(r), NULL, r, "[%s] Failed to construct ArrayList.", GetErrorMessage(r));\r
-\r
- __pFinalOutList = std::move(pFinalOutList);\r
-\r
- switch (__contentType)\r
- {\r
- case CONTENT_TYPE_OTHER:\r
- //fall through\r
- case CONTENT_TYPE_IMAGE:\r
- maxCols = MAX_QUERY_COLUMNS_FOR_IMAGE_OTHERS;\r
- break;\r
- case CONTENT_TYPE_VIDEO:\r
- maxCols = MAX_QUERY_COLUMNS_FOR_VIDEO;\r
- break;\r
- case CONTENT_TYPE_AUDIO:\r
- //fall through\r
- case CONTENT_TYPE_ALL:\r
- maxCols = MAX_QUERY_COLUMNS;\r
- break;\r
- default:\r
- break;\r
- }\r
-\r
- for (colIndex = 0; colIndex < maxCols; colIndex++)\r
- {\r
- ospColumnName.Clear();\r
- slpColumnName.Clear();\r
-\r
- ospColumnName = dbfieldinfo[colIndex].dbFieldOspName ;\r
- slpColumnName = dbfieldinfo[colIndex].dbFieldSlpName ;\r
-\r
- ospColumnName.ToUpper();\r
- columnName.ToUpper();\r
- if (columnName == ospColumnName)\r
- {\r
- r = FillColumnsList(pageNo, countPerPage, totalPageCount, totalCount, colIndex);\r
- SysTryReturn(NID_CNT, r == E_SUCCESS, NULL, r, "[%s] FillColumnsList Failed.", GetErrorMessage(r));\r
- break;\r
- }\r
- }\r
- if (colIndex == maxCols)\r
- {\r
- r = E_INVALID_ARG;\r
- SysTryReturn(NID_CNT, r == E_SUCCESS, NULL, r, "[E_INVALID_ARG] invalid column.");\r
- }\r
- }\r
- SetLastResult(r);\r
- return __pFinalOutList.release();\r
-}\r
-\r
-// prepares query expression to be used in group api. colIndex is mapped to actual group value.\r
-media_group_e\r
-_ContentSearchImpl::GetIndexAndCreateQueryExp(int colIndex) const\r
-{\r
- media_group_e groupIndex = MEDIA_CONTENT_GROUP_DISPLAY_NAME;;\r
- switch (colIndex)\r
- {\r
- case 0://"ContentType", "MEDIA_TYPE"\r
- groupIndex = MEDIA_CONTENT_GROUP_TYPE;\r
- __inputExpr = "MEDIA_TYPE IS NOT NULL";\r
- break;\r
- case 1://"ContentFileName", "MEDIA_DISPLAY_NAME"\r
- groupIndex = MEDIA_CONTENT_GROUP_DISPLAY_NAME;\r
- __inputExpr = "MEDIA_DISPLAY_NAME IS NOT NULL";\r
- break;\r
- case 2://"ContentName", "MEDIA_CONTENT_NAME"\r
- groupIndex = MEDIA_CONTENT_GROUP_CONTENT_NAME;\r
- __inputExpr = "MEDIA_CONTENT_NAME IS NOT NULL";\r
- break;\r
- case 3://"Category", "MEDIA_CATEGORY"\r
- groupIndex = MEDIA_CONTENT_GROUP_CATEGORY;\r
- __inputExpr = "MEDIA_CATEGORY IS NOT NULL";\r
- break;\r
- case 4://"Author", "MEDIA_AUTHOR"\r
- groupIndex = MEDIA_CONTENT_GROUP_AUTHOR;\r
- __inputExpr = "MEDIA_AUTHOR IS NOT NULL";\r
- break;\r
- case 5://"keyword", "MEDIA_KEYWORD"\r
- groupIndex = MEDIA_CONTENT_GROUP_KEYWORD;\r
- __inputExpr = "MEDIA_KEYWORD IS NOT NULL";\r
- break;\r
- case 6://"Provider", "MEDIA_PROVIDER"\r
- groupIndex = MEDIA_CONTENT_GROUP_PROVIDER;\r
- __inputExpr = "MEDIA_PROVIDER IS NOT NULL";\r
- break;\r
- case 7://"Rating", "MEDIA_AGE_RATING"\r
- groupIndex = MEDIA_CONTENT_GROUP_AGE_RATING;\r
- __inputExpr = "MEDIA_AGE_RATING IS NOT NULL";\r
- break;\r
- case 8://"LocationTag", "MEDIA_LOCATION_TAG"\r
- groupIndex = MEDIA_CONTENT_GROUP_LOCATION_TAG;\r
- __inputExpr = "MEDIA_LOCATION_TAG IS NOT NULL";\r
- break;\r
- case 9://"ContentSize", "MEDIA_SIZE"\r
- groupIndex = MEDIA_CONTENT_GROUP_SIZE;\r
- __inputExpr = "MEDIA_SIZE IS NOT NULL";\r
- break;\r
- case 10://"DateTime", "MEDIA_ADDED_TIME"\r
- groupIndex = MEDIA_CONTENT_GROUP_ADDED_TIME;\r
- __inputExpr = "MEDIA_ADDED_TIME IS NOT NULL";\r
- break;\r
- case 11://"Latitude", "MEDIA_LATITUDE"\r
- groupIndex = MEDIA_CONTENT_GROUP_LATITUDE;\r
- __inputExpr = "MEDIA_LATITUDE IS NOT NULL";\r
- break;\r
- case 12://"Longitude", "MEDIA_LONGITUDE"\r
- groupIndex = MEDIA_CONTENT_GROUP_LONGITUDE;\r
- __inputExpr = "MEDIA_LONGITUDE IS NOT NULL";\r
- break;\r
- case 13://"Altitude", "MEDIA_ALTITUDE"\r
- groupIndex = MEDIA_CONTENT_GROUP_ALTITUDE;\r
- __inputExpr = "MEDIA_ALTITUDE IS NOT NULL";\r
- break;\r
- case 14://"Title", "MEDIA_TITLE"\r
- groupIndex = MEDIA_CONTENT_GROUP_TITLE;\r
- __inputExpr = "MEDIA_TITLE IS NOT NULL";\r
- break;\r
- case 15://"Artist", "MEDIA_ARTIST"\r
- groupIndex = MEDIA_CONTENT_GROUP_ARTIST;\r
- __inputExpr = "MEDIA_ARTIST IS NOT NULL";\r
- break;\r
- case 16://"Genre", "MEDIA_GENRE"\r
- groupIndex = MEDIA_CONTENT_GROUP_GENRE;\r
- __inputExpr = "MEDIA_GENRE IS NOT NULL";\r
- break;\r
- case 17://"Year", "MEDIA_YEAR"\r
- groupIndex = MEDIA_CONTENT_GROUP_YEAR;\r
- __inputExpr = "MEDIA_YEAR IS NOT NULL";\r
- break;\r
- case 18://"Composer", "MEDIA_COMPOSER"\r
- groupIndex = MEDIA_CONTENT_GROUP_COMPOSER;\r
- __inputExpr = "MEDIA_COMPOSER IS NOT NULL";\r
- break;\r
- case 19://"Album", "MEDIA_ALBUM"\r
- __inputExpr = "MEDIA_ALBUM IS NOT NULL";\r
- break;\r
- default:\r
- break;\r
- }\r
- return groupIndex;\r
-}\r
-\r
-// Fills given column value list and destroys filter handle\r
-result\r
-_ContentSearchImpl::FillColumnsList(int colIndex) const\r
-{\r
- result r = E_SUCCESS;\r
- int ret = MEDIA_CONTENT_ERROR_NONE;\r
- int totalCount = 0;\r
- media_group_e groupIndex = GetIndexAndCreateQueryExp(colIndex);\r
-\r
- r = CreateQueryFilter(true);\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "CreateQueryFilter Failed.");\r
-\r
- if (colIndex == ALBUM_COLUMN_NUM)\r
- {\r
- ret = media_album_get_album_count_from_db(*(__pFilterHandle.get()), &totalCount);\r
- }\r
- else\r
- {\r
- ret = media_group_get_group_count_from_db(*(__pFilterHandle.get()), groupIndex, &totalCount);\r
- }\r
- r = MapCoreErrorToNativeResult(ret);\r
- SysTryReturnResult(NID_CNT, ret == MEDIA_CONTENT_ERROR_NONE, r, "Failed to perform media_album/group count_from_db operation.");\r
-\r
- SysLog(NID_CNT, "totalCount = %d for media_album/group count_from_db", totalCount);\r
-\r
- if (totalCount > 0)\r
- {\r
- if (colIndex == ALBUM_COLUMN_NUM)\r
- {\r
- r = ExecuteAndFillAlbumValues();\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "ExecuteAndFillAlbumValues Failed.");\r
- }\r
- else\r
- {\r
- r = ExecuteAndFillGetValueListN(groupIndex, colIndex);\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "ExecuteAndFillGetValueListN Failed.");\r
- }\r
- }\r
- return r;\r
-}\r
-\r
-// prepares input expression to be sent for create filter and fills given column value list\r
-result\r
-_ContentSearchImpl::FillColumnsList(int pageNo, int countPerPage, int& totalPageCount, int& totalCount, int colIndex) const\r
-{\r
- result r = E_SUCCESS;\r
- int ret = MEDIA_CONTENT_ERROR_NONE;\r
- int offset = 0;\r
- totalPageCount = 0;\r
- totalCount = 0;\r
- media_group_e groupIndex = GetIndexAndCreateQueryExp(colIndex);\r
-\r
- r = CreateQueryFilter(true);\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "CreateQueryFilter Failed.");\r
-\r
- if (colIndex == ALBUM_COLUMN_NUM)\r
- {\r
- ret = media_album_get_album_count_from_db(*(__pFilterHandle.get()), &totalCount);\r
- }\r
- else\r
- {\r
- ret = media_group_get_group_count_from_db(*(__pFilterHandle.get()), groupIndex, &totalCount);\r
- }\r
- r = MapCoreErrorToNativeResult(ret);\r
- SysTryReturnResult(NID_CNT, ret == MEDIA_CONTENT_ERROR_NONE, r, "Failed to perform media_album/group count_from_db operation.");\r
-\r
- SysLog(NID_CNT, "totalCount = %d for media_album/group count_from_db", totalCount);\r
-\r
- if (totalCount > 0)\r
- {\r
- if ((totalCount % countPerPage) == 0)\r
- {\r
- totalPageCount = totalCount / countPerPage;\r
- }\r
- else\r
- {\r
- totalPageCount = (totalCount / countPerPage) + 1;\r
- }\r
-\r
- if ((pageNo < 1) || (pageNo > totalPageCount))\r
- {\r
- r = E_INVALID_ARG;\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "(pageNo < 1) || (pageNo > totalPageCount).");\r
- }\r
-\r
- offset = (pageNo * countPerPage) - countPerPage;\r
-\r
- SysLog(NID_CNT, "GetValueListN totalCount [%d] totalPageCount[%d] __countPerPage[%d] __pageNo[%d] offset[%d]",\r
- totalCount, totalPageCount, countPerPage, pageNo, offset);\r
-\r
- ret = media_filter_set_offset(*(__pFilterHandle.get()),offset,countPerPage);\r
- r = MapCoreErrorToNativeResult(ret);\r
- SysTryReturnResult(NID_CNT, ret == MEDIA_CONTENT_ERROR_NONE, r, "failed to perform media_filter_set_offset operation.");\r
-\r
- if (colIndex == ALBUM_COLUMN_NUM)\r
- {\r
- r = ExecuteAndFillAlbumValues();\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "ExecuteAndFillAlbumValues Failed.");\r
- }\r
- else\r
- {\r
- r = ExecuteAndFillGetValueListN(groupIndex, colIndex);\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "ExecuteAndFillGetValueListN Failed.");\r
- }\r
-\r
- }\r
- else if (pageNo > 1)\r
- {\r
- r = E_INVALID_ARG;\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "(pageNo > 1) and (totalcount = 0).");\r
- }\r
-\r
- return r;\r
-}\r
-\r
-// fills given column value list for GetValuelistN api\r
-result\r
-_ContentSearchImpl::ExecuteAndFillGetValueListN(media_group_e groupIndex, int colIndex) const\r
-{\r
- SysLog(NID_CNT, "Enter\n");\r
-\r
- int ret = MEDIA_CONTENT_ERROR_NONE;\r
- result r = E_SUCCESS;\r
- result res = E_SUCCESS;\r
- std::unique_ptr<GList, SearchGListDeleter> pItemList;\r
- GList* pTemp = NULL;\r
-\r
- std::unique_ptr<Object> pValue;\r
-\r
- DateTime dateTime;\r
-\r
- long long contentSize = 0;\r
- long long addedTime = 0;\r
-\r
- double dVal = 0;\r
- char *pColumnVal = null;\r
- int contentType = 0;\r
-\r
- pTemp = pItemList.get();\r
-\r
- ret = media_group_foreach_group_from_db(*(__pFilterHandle.get()), groupIndex, GroupItemCb, &pTemp);\r
- r = MapCoreErrorToNativeResult(ret);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "Failed to perform media_group_foreach_group_from_db operation.");\r
-\r
- SysTryReturnResult(NID_CNT, pTemp != NULL, r, "media_info_foreach_media_from_db pTemp is null.");\r
-\r
- for (int idx = 0; idx < (int)g_list_length(pTemp); idx++)\r
- {\r
- SysLog(NID_CNT, "idx = %d and (int)g_list_length(pItemList) = %d", idx, (int)g_list_length(pTemp));\r
-\r
- pColumnVal = (char *)g_list_nth_data(pTemp, idx);\r
-\r
- String strColVal(pColumnVal);\r
-\r
- _ContentUtility::DoSafeFree(pColumnVal);\r
-\r
- SysLog(NID_CNT, "pColumnVal = %ls", strColVal.GetPointer());\r
-\r
- switch (colIndex)\r
- {\r
- case 0://"ContentType", "MEDIA_TYPE"\r
- if ((strColVal.CompareTo(L"Unknown") != 0) && (!strColVal.IsEmpty()))\r
- {\r
- res = Integer::Parse(strColVal, contentType);\r
- SysTryLog(NID_CNT, res == E_SUCCESS, "[%s] Integer parse failed.", GetErrorMessage(res));\r
- }\r
- switch ((media_content_type_e)contentType)\r
- {\r
- case MEDIA_CONTENT_TYPE_OTHERS:\r
- pValue.reset(new (std::nothrow) String(CONTENT_TYPE_OTHER));\r
- SysLog(NID_CNT, "mediaType = CONTENT_TYPE_OTHER");\r
- break;\r
- case MEDIA_CONTENT_TYPE_IMAGE:\r
- pValue.reset(new (std::nothrow) String(CONTENT_TYPE_IMAGE));\r
- SysLog(NID_CNT, "mediaType = CONTENT_TYPE_IMAGE");\r
- break;\r
- case MEDIA_CONTENT_TYPE_SOUND:\r
- //fall through\r
- case MEDIA_CONTENT_TYPE_MUSIC:\r
- pValue.reset(new (std::nothrow) String(CONTENT_TYPE_AUDIO));\r
- SysLog(NID_CNT, "mediaType = CONTENT_TYPE_AUDIO");\r
- break;\r
- case MEDIA_CONTENT_TYPE_VIDEO:\r
- pValue.reset(new (std::nothrow) String(CONTENT_TYPE_VIDEO));\r
- SysLog(NID_CNT, "mediaType = CONTENT_TYPE_VIDEO");\r
- break;\r
- default:\r
- break;\r
- }\r
- break;\r
- case 1://"ContentFileName", "MEDIA_DISPLAY_NAME"\r
- //fall through\r
- case 2://"ContentName", "MEDIA_CONTENT_NAME"\r
- //fall through\r
- case 3://"Category", "MEDIA_CATEGORY"\r
- //fall through\r
- case 4://"Author", "MEDIA_AUTHOR"\r
- //fall through\r
- case 5://"keyword", "MEDIA_KEYWORD"\r
- //fall through\r
- case 6://"Provider", "MEDIA_PROVIDER"\r
- //fall through\r
- case 7://"Rating", "MEDIA_AGE_RATING"\r
- //fall through\r
- case 8://"LocationTag", "MEDIA_LOCATION_TAG"\r
- //fall through\r
- case 14://"Title", "MEDIA_TITLE"\r
- //fall through\r
- case 15://"Artist", "MEDIA_ARTIST"\r
- //fall through\r
- case 16://"Genre", "MEDIA_GENRE"\r
- //fall through\r
- case 17://"Year", "MEDIA_YEAR"\r
- //fall through\r
- case 18://"Composer", "MEDIA_COMPOSER"\r
-\r
- pValue.reset(new (std::nothrow) String(strColVal));\r
- break;\r
-\r
- case 9://"ContentSize", "MEDIA_SIZE" \r
- if ((strColVal.CompareTo(L"Unknown") != 0) && (!strColVal.IsEmpty()))\r
- {\r
- res = LongLong::Parse(strColVal, contentSize);\r
- SysTryLog(NID_CNT, res == E_SUCCESS, "[%s] LongLong parse failed.", GetErrorMessage(res));\r
- }\r
-\r
- pValue.reset(new (std::nothrow) LongLong(contentSize));\r
- break;\r
- case 10://"DateTime", "MEDIA_ADDED_TIME" \r
- if ((strColVal.CompareTo(L"Unknown") != 0) && (!strColVal.IsEmpty()))\r
- {\r
- res = LongLong::Parse(strColVal, addedTime);\r
- SysTryLog(NID_CNT, res == E_SUCCESS, "[%s] LongLong parse failed.", GetErrorMessage(res));\r
- }\r
-\r
- res = dateTime.SetValue(1970, 1, 1);\r
- SysTryLog(NID_CNT, res == E_SUCCESS, "[%s] dateTime.SetValue failed.", GetErrorMessage(res));\r
-\r
- res = dateTime.AddSeconds(addedTime);\r
- SysTryLog(NID_CNT, res == E_SUCCESS, "[%s] dateTime.AddSeconds failed.", GetErrorMessage(res));\r
-\r
- SysLog(NID_CNT, "DateTime : %ls", dateTime.ToString().GetPointer());\r
-\r
- pValue.reset(new (std::nothrow) DateTime(dateTime));\r
-\r
- break;\r
- case 11://"Latitude", "MEDIA_LATITUDE"\r
- //fall through\r
- case 12://"Longitude", "MEDIA_LONGITUDE"\r
- //fall through\r
- case 13://"Altitude", "MEDIA_ALTITUDE"\r
- if ((strColVal.CompareTo(L"Unknown") != 0) && (!strColVal.IsEmpty()))\r
- {\r
- res = Double::Parse(strColVal, dVal);\r
- SysTryLog(NID_CNT, res == E_SUCCESS, "[%s] double parse failed.", GetErrorMessage(res));\r
- }\r
- pValue.reset(new (std::nothrow) Double(dVal));\r
- break;\r
-\r
- case 19://"Album", "MEDIA_ALBUM"\r
- break;\r
- default:\r
- break;\r
- }\r
- if (pValue.get() != NULL)\r
- {\r
- r = __pFinalOutList->Add(*(pValue.release()));\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "Failed to perform arraylist Add operation.");\r
- }\r
- }\r
-\r
- return r;\r
-}\r
-\r
-result\r
-_ContentSearchImpl::ExecuteAndFillAlbumValues(void) const\r
-{\r
- int ret = MEDIA_CONTENT_ERROR_NONE;\r
- result r = E_SUCCESS;\r
- std::unique_ptr<GList, SearchGListDeleter> pItemList;\r
- GList* pTemp = NULL;\r
- std::unique_ptr<media_album_s, AlbumHandleDeleter> pAlbumHandle;\r
- std::unique_ptr<media_album_s, AlbumHandleDeleter> pTempAlbumHandle;\r
-\r
- char* pName = NULL;\r
- std::unique_ptr<char, CharDeleter> pAlbumName;\r
- std::unique_ptr< String > pValue;\r
- int lastIndex = 0;\r
-\r
- pTemp = pItemList.get();\r
-\r
- ret = media_album_foreach_album_from_db(*(__pFilterHandle.get()), AlbumItemCb, &pTemp);\r
- r = MapCoreErrorToNativeResult(ret);\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "Failed to perform media_album_foreach_album_from_db operation.");\r
- SysTryReturnResult(NID_CNT, pTemp != NULL, r, "media_info_foreach_media_from_db pTemp is null.");\r
-\r
- for (int idx = 0; idx < (int)g_list_length(pTemp); idx++)\r
- {\r
- pAlbumHandle.reset(static_cast<media_album_h>(g_list_nth_data(pTemp, idx)));\r
- ret = media_album_get_name(pAlbumHandle.get(), &pName);\r
- r = MapCoreErrorToNativeResult(ret);\r
- SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform media_album_get_name.");\r
- \r
- if (pName != NULL)\r
- {\r
- SysLog(NID_CNT, "pColumnVal = %s", pName);\r
-\r
- pAlbumName.reset(pName);\r
- pValue.reset(new (std::nothrow) String(pAlbumName.get()));\r
- SysTryReturnResult(NID_CNT, pValue != NULL, E_OUT_OF_MEMORY, "media_info_foreach_media_from_db pTemp is null.");\r
-\r
- if (idx == 0)\r
- {\r
- r = __pFinalOutList->Add(pValue.get());\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "Failed to perform arraylist Add operation.");\r
- pValue.release();\r
- }\r
- else\r
- {\r
- String* pTempNameList(static_cast< String* >(__pFinalOutList->GetAt(lastIndex)));\r
-\r
- if (pValue->CompareTo(*pTempNameList) != 0)\r
- {\r
- r = __pFinalOutList->Add(pValue.get());\r
- SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "Failed to perform arraylist Add operation.");\r
-\r
- pValue.release();\r
- lastIndex++;\r
- }\r
- }\r
- }\r
- }\r
-\r
- return r;\r
-}\r
-\r
-result\r
-_ContentSearchImpl::MapCoreErrorToNativeResult(int reason) const\r
-{\r
- result r = E_SUCCESS;\r
-\r
- switch (reason)\r
- {\r
- case MEDIA_CONTENT_ERROR_NONE:\r
- r = E_SUCCESS;\r
- break;\r
-\r
- case MEDIA_CONTENT_ERROR_INVALID_PARAMETER:\r
- r = E_INVALID_ARG;\r
- SysLog(NID_CNT, "MEDIA_CONTENT_ERROR_INVALID_PARAMETER");\r
- break;\r
-\r
- case MEDIA_CONTENT_ERROR_DB_FAILED:\r
- r = E_SYSTEM;\r
- SysLog(NID_CNT, "MEDIA_CONTENT_ERROR_DB_FAILED");\r
- break;\r
-\r
- case MEDIA_CONTENT_ERROR_OUT_OF_MEMORY:\r
- r = E_OUT_OF_MEMORY;\r
- SysLog(NID_CNT, "MEDIA_CONTENT_ERROR_OUT_OF_MEMORY");\r
- break;\r
-\r
- default:\r
- SysLog(NID_CNT, "default");\r
- r = E_SYSTEM;\r
- break;\r
- }\r
- return r;\r
-}\r
-\r
-//Callback function registered to each media info details\r
-// all items are appened to the list\r
-bool\r
-MediaItemCb(media_info_h media, void* pUserdata)\r
-{\r
- int ret = MEDIA_CONTENT_ERROR_NONE;\r
- media_info_h new_media = NULL;\r
- ret = media_info_clone(&new_media, media);\r
- SysTryLog(NID_CNT, ret == MEDIA_CONTENT_ERROR_NONE, "[E_SYSTEM] Failed to perform media_info_clone");\r
-\r
- GList** pList = (GList**)pUserdata;\r
- *pList = g_list_append(*pList, new_media);\r
-\r
- return true;\r
-}\r
-\r
-//Callback function registered for column values\r
-// all items are appened to the list\r
-bool\r
-GroupItemCb(const char* pGroupName, void* pUserdata)\r
-{\r
- char* pGrpName = strdup(pGroupName);\r
- GList** pList = (GList**)pUserdata;\r
- *pList = g_list_append(*pList, pGrpName);\r
-\r
- return true;\r
-}\r
-\r
-//Callback function registered to each media info details\r
-// all items are appened to the list\r
-bool\r
-AlbumItemCb(media_album_h album, void* pUserdata)\r
-{\r
- int ret = MEDIA_CONTENT_ERROR_NONE;\r
- media_album_h new_album = NULL;\r
- ret = media_album_clone(&new_album, album);\r
- SysTryLog(NID_CNT, ret == MEDIA_CONTENT_ERROR_NONE, "[E_SYSTEM] Failed to perform media_album_clone");\r
-\r
- GList** pList = (GList**)pUserdata;\r
- *pList = g_list_append(*pList, new_album);\r
-\r
- return true;\r
-}\r
-\r
-}}\r
+//
+// Copyright (c) 2012 Samsung Electronics Co., Ltd.
+//
+// Licensed under the Apache License, Version 2.0 (the License);
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+/**
+ * @file FCnt_ContentSearchImpl.cpp
+ * @brief This is the implementation file for the %_ContentSearchImpl class.
+ *
+ * This file contains implementation of the %_ContentSearchImpl class.
+ */
+
+#include <new>
+#include <time.h>
+#include <FBaseSysLog.h>
+#include <FBaseInteger.h>
+#include <FBaseLongLong.h>
+#include <FBaseFloat.h>
+#include <FBaseColIList.h>
+#include <FBaseUtilStringTokenizer.h>
+#include <FCntContentSearch.h>
+#include <FCntContentSearchResult.h>
+#include <FSysEnvironment.h>
+#include <FApp_AppInfo.h>
+#include <FBase_StringConverter.h>
+#include <FBase_LocalizedNumParser.h>
+#include <FIo_FileImpl.h>
+#include "FCnt_ContentUtility.h"
+#include "FCnt_ContentSearchImpl.h"
+#include "FCnt_ContentInfoImpl.h"
+#include "FCnt_ImageContentInfoImpl.h"
+#include "FCnt_AudioContentInfoImpl.h"
+#include "FCnt_VideoContentInfoImpl.h"
+#include "FCnt_OtherContentInfoImpl.h"
+#include "FCnt_ContentInfoHelper.h"
+
+using namespace Tizen::App;
+using namespace Tizen::Base;
+using namespace Tizen::Base::Collection;
+using namespace Tizen::Base::Utility;
+using namespace Tizen::Io;
+using namespace Tizen::System;
+
+namespace Tizen { namespace Content
+{
+
+static const int QUERY_LENGTH = 4096;
+
+// Declaration for Callback function registered to each media info details
+bool MediaItemCb(media_info_h media, void* pUserdata);
+// Declaration for Callback function registered to each column details
+bool GroupItemCb(const char* pGroupName, void* pUserdata);
+// Declaration for Callback function registered to each album details
+bool AlbumItemCb(media_album_h album, void* pUserdata);
+
+// Default constructor
+_ContentSearchImpl::_ContentSearchImpl(void)
+ : __contentType(CONTENT_TYPE_UNKNOWN)
+ , __pFinalOutList(NULL)
+ , __inputExpr(L"")
+ , __inputColumnName(L"")
+ , __inputSortOrder(SORT_ORDER_NONE)
+ , __pFilterHandle(NULL)
+{
+ SysLog(NID_CNT, "Enter\n");
+}
+
+
+// Default destructor (disconnects the DB connection)
+_ContentSearchImpl::~_ContentSearchImpl(void)
+{
+ SysLog(NID_CNT, "Enter\n");
+
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+ result r = E_SUCCESS;
+
+ ret = media_content_disconnect();
+ r = MapCoreErrorToNativeResult(ret);
+ SysTryLog(NID_CNT, r == E_SUCCESS, "[%s] Propagated in ~_ContentSearchImpl", GetErrorMessage(r));
+}
+
+ _ContentSearchImpl*
+ _ContentSearchImpl::GetInstance(ContentSearch& contentSearch)
+{
+ return contentSearch.__pImpl;
+}
+
+const _ContentSearchImpl*
+_ContentSearchImpl::GetInstance(const ContentSearch& contentSearch)
+{
+ return contentSearch.__pImpl;
+}
+
+//make a connection to DB
+result
+_ContentSearchImpl::Construct(ContentType type)
+{
+ SysLog(NID_CNT, "Enter\n");
+
+ result r = E_SUCCESS;
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+
+ ret = media_content_connect();
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS , E_SYSTEM, "Failed to perform media_content_connect operation.");
+
+ __contentType = type;
+
+ return r;
+}
+
+// Creates a filter for the input query string along with content type
+// Initializes filter handle
+// Image - MEDIA_TYPE=0
+// Vide0 - MEDIA_TYPE=1
+// Audio - MEDIA_TYPE=2 or MEDIA_TYPE=3
+// Others - MEDIA_TYPE=4
+// All - none
+// Appends MEDIA_TYPE with "AND" (if the input expression is not empty and content type is not ALL) and input expression
+// Sets the condition and order.
+// If any argument is not proper E_INVALID_ARG is returned
+result
+_ContentSearchImpl::CreateQueryFilter(bool isAndAppendReq) const
+{
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+ result r = E_SUCCESS;
+
+ std::unique_ptr<char[]> pInputCond;
+ std::unique_ptr<char[]> pSortCol;
+
+ String inputCondition;
+ String slpColumn;
+
+ filter_h tempFilter = NULL;
+
+ ret = media_filter_create(&tempFilter);
+ SysTryReturnResult(NID_CNT, ret == MEDIA_CONTENT_ERROR_NONE, E_SYSTEM, "Failed to perform media_filter_create operation.");
+
+ std::unique_ptr<filter_s, SearchFilterHandleDeleter> pFilterHandle(tempFilter);
+ SysTryReturnResult(NID_CNT, pFilterHandle != null, E_OUT_OF_MEMORY, "pFilterHandle is null.");
+
+ switch (__contentType)
+ {
+ // Image-0,video-1,sound-2,music-3,other-4
+ case CONTENT_TYPE_OTHER:
+ inputCondition = "MEDIA_TYPE=4 ";
+ break;
+ case CONTENT_TYPE_IMAGE:
+ inputCondition = "MEDIA_TYPE=0 ";
+ break;
+ case CONTENT_TYPE_AUDIO:
+ inputCondition = "(MEDIA_TYPE=2 or MEDIA_TYPE=3) ";
+ break;
+ case CONTENT_TYPE_VIDEO:
+ inputCondition = "MEDIA_TYPE=1 ";
+ break;
+ case CONTENT_TYPE_ALL:
+ //If content type is CONTENT_TYPE_ALL, then MEDIA_TYPE is empty
+ break;
+ default:
+ break;
+ }
+
+ if (!__inputExpr.IsEmpty())
+ {
+ if (isAndAppendReq && (!inputCondition.IsEmpty())) //For CONTENT_TYPE_ALL inputCondition is empty
+ {
+ r = inputCondition.Append("AND ");
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform append operation.");
+ }
+
+ r = inputCondition.Append(__inputExpr);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform append operation.");
+ }
+
+ if (!inputCondition.IsEmpty())
+ {
+ //CopyToCharArrayN: utility function, converts a osp string to char*
+ pInputCond = std::unique_ptr<char[]>(_StringConverter::CopyToCharArrayN(inputCondition));
+ SysTryReturnResult(NID_CNT, pInputCond, E_OUT_OF_MEMORY, "pInputCond is NULL.");
+
+ SysLog(NID_CNT, "pInputCond = %s", pInputCond.get());
+
+ ret = media_filter_set_condition(pFilterHandle.get(), pInputCond.get(), MEDIA_CONTENT_COLLATE_DEFAULT);
+ SysTryReturnResult(NID_CNT, ret == MEDIA_CONTENT_ERROR_NONE, E_SYSTEM, "Failed to perform media_filter_set_condition operation.");
+ }
+
+ if (!__inputColumnName.IsEmpty()) // SortColumn is optional in case of SearchN
+ {
+ //__inputColumnName (osp column name) is replaced with slpColumn (slp column name).
+ r = GetSlpColumnName(slpColumn);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform GetSlpColumnName operation.");
+
+ //CopyToCharArrayN: utility function, converts a osp string to char*
+
+ pSortCol = std::unique_ptr<char[]>(_StringConverter::CopyToCharArrayN(slpColumn));
+ SysTryReturnResult(NID_CNT, pSortCol, E_OUT_OF_MEMORY, "pSortCol is NULL.");
+
+ if (__inputSortOrder == SORT_ORDER_ASCENDING)
+ {
+ ret = media_filter_set_order(pFilterHandle.get(), MEDIA_CONTENT_ORDER_ASC, pSortCol.get(), MEDIA_CONTENT_COLLATE_NOCASE);
+ SysTryReturnResult(NID_CNT, ret == MEDIA_CONTENT_ERROR_NONE, E_SYSTEM, "Failed to perform media_filter_set_order operation.");
+ }
+ else if (__inputSortOrder == SORT_ORDER_DESCENDING)
+ {
+ ret = media_filter_set_order(pFilterHandle.get(), MEDIA_CONTENT_ORDER_DESC, pSortCol.get(), MEDIA_CONTENT_COLLATE_NOCASE);
+ SysTryReturnResult(NID_CNT, ret == MEDIA_CONTENT_ERROR_NONE, E_SYSTEM, "Failed to perform media_filter_set_order operation.");
+ }
+ }
+
+ __pFilterHandle.reset(pFilterHandle.release());
+
+ return r;
+}
+
+// Osp column names are mapped with slp column names
+// CONTENT_TYPE_OTHER and CONTENT_TYPE_IMAGE (0 - 13 ) are valid columns
+// CONTENT_TYPE_VIDEO (0 - 16 ) are valid columns
+// CONTENT_TYPE_ALL and CONTENT_TYPE_VIDEO (0 - 18 ) are valid columns
+// if the given osp column is out of the specified range of the type, E_INVALID_ARG is retuned.
+result
+_ContentSearchImpl::GetSlpColumnName(String& inputCol) const
+{
+ String ospColumnName(L"");
+ String slpColumnName(L"");
+ String columnName(__inputColumnName);
+ result r = E_SUCCESS;
+ int maxCols = 0;
+ switch (__contentType)
+ {
+ case CONTENT_TYPE_OTHER:
+ //fall through
+ case CONTENT_TYPE_IMAGE:
+ maxCols = MAX_QUERY_COLUMNS_FOR_IMAGE_OTHERS;
+ break;
+ case CONTENT_TYPE_VIDEO:
+ maxCols = MAX_QUERY_COLUMNS_FOR_VIDEO;
+ break;
+ case CONTENT_TYPE_AUDIO:
+ //fall through
+ case CONTENT_TYPE_ALL:
+ maxCols = MAX_QUERY_COLUMNS;
+ break;
+ default:
+ break;
+ }
+ for (int colIndex = 0; colIndex < maxCols; colIndex++)
+ {
+ ospColumnName.Clear();
+ slpColumnName.Clear();
+
+ ospColumnName = dbfieldinfo[colIndex].dbFieldOspName ;
+ slpColumnName = dbfieldinfo[colIndex].dbFieldSlpName ;
+
+ ospColumnName.ToUpper();
+ columnName.ToUpper();
+ if (columnName == ospColumnName)
+ {
+ inputCol = slpColumnName;
+ return r;
+ }
+ }
+ return E_INVALID_ARG;
+}
+
+//If the input expression contains any osp column name, it will be replaced with slp column name.
+// only CONTENT_TYPE_AUDIO and CONTENT_TYPE_ALL allowed to use all given columns
+// so, check for invalid column for CONTENT_TYPE_OTHER,CONTENT_TYPE_IMAGE and CONTENT_TYPE_VIDEO.
+// all the osp columns in the expression should be replaced with slp column names.
+// ' is used as a delimeter in parsing user query. so, \\' is saved as a special@apostrophe string.
+// \\' is replaced with '', which considers ' as normal character.
+
+result
+_ContentSearchImpl::ReplaceOspColumnNameWithSlp(void) const
+{
+ String ospColumnName(L"");
+ String slpColumnName(L"");
+ String splApostrophe(L"special@apostrophe");
+ result r = E_SUCCESS;
+ int maxCols = 0;
+
+ int indexOf = 0;
+
+ String strToBeReplaced(L"\\'");
+ int strLen = strToBeReplaced.GetLength();
+ int startIndex = 0;
+
+ while(E_SUCCESS == __inputExpr.IndexOf(strToBeReplaced,startIndex,indexOf))
+ {
+ int lenAfterSubStr = indexOf + strLen;
+ while ((lenAfterSubStr < __inputExpr.GetLength()) && (__inputExpr[lenAfterSubStr] == ' '))
+ {
+ lenAfterSubStr++;
+ }
+ if ((lenAfterSubStr < __inputExpr.GetLength()) && ((__inputExpr[lenAfterSubStr] == '\'') ||
+ ((!__inputExpr.StartsWith(L"AND ", lenAfterSubStr)) && (!__inputExpr.StartsWith(L"OR ", lenAfterSubStr)))))
+ {
+ r = __inputExpr.Remove(indexOf,strLen);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "Failed to perform Remove operation.");
+ r = __inputExpr.Insert(splApostrophe,indexOf);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "Failed to perform Insert operation.");
+ startIndex = indexOf + splApostrophe.GetLength();
+ }
+ else
+ {
+ startIndex = lenAfterSubStr;
+ }
+ }
+
+ SysLog(NID_CNT, "__inputExpr after splApostrophe append = %ls", __inputExpr.GetPointer());
+
+ switch (__contentType)
+ {
+ case CONTENT_TYPE_OTHER:
+ //fall through
+ case CONTENT_TYPE_IMAGE:
+ r = CheckInvalidColumnInQuery();
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_INVALID_ARG, "Invalid Column In QueryString.");
+ maxCols = MAX_QUERY_COLUMNS_FOR_IMAGE_OTHERS;
+ break;
+ case CONTENT_TYPE_VIDEO:
+ r = CheckInvalidColumnInQuery();
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_INVALID_ARG, "Invalid Column In QueryString.");
+ maxCols = MAX_QUERY_COLUMNS_FOR_VIDEO;
+ break;
+ case CONTENT_TYPE_AUDIO:
+ //fall through
+ case CONTENT_TYPE_ALL:
+ maxCols = MAX_QUERY_COLUMNS;
+ break;
+ default:
+ break;
+ }
+ for (int colIndex = 0; colIndex < maxCols; colIndex++)
+ {
+ ospColumnName.Clear();
+ slpColumnName.Clear();
+
+ ospColumnName = dbfieldinfo[colIndex].dbFieldOspName ;
+ slpColumnName = dbfieldinfo[colIndex].dbFieldSlpName ;
+
+ ReplaceString(ospColumnName,slpColumnName);
+ }
+
+ // Append ESCAPE '\' for LIKE query
+ r = AppendEscapeKeywordForLikeQuery();
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "AppendEscapeKeywordForLikeQuery failed.");
+
+ r = ReplaceDateTimeStringWithInt();
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_INVALID_ARG, "ReplaceDateTimeStringWithInt failed.");
+
+ // replace splApostrophe string with actual
+ r = __inputExpr.Replace(splApostrophe, "''");
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string Replace failed.");
+
+ return r;
+}
+
+//This function is to appened ESCAPE keyword for _ and % special characters in LIKE query.
+
+result
+_ContentSearchImpl::AppendEscapeKeywordForLikeQuery(void) const
+{
+ String delim = L"'"; //Delimeters is ' .
+ result r = E_SUCCESS;
+ bool isCol = true;
+ bool isAppendEscape = false;
+ String token;
+ String tokenUpper;
+ String inputExpr = __inputExpr;
+
+ // Create a StringTokenizer instance
+ StringTokenizer strTok(inputExpr, delim);
+
+ inputExpr.Clear();
+
+ while (strTok.HasMoreTokens())
+ {
+ r = strTok.GetNextToken(token);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "GetNextToken failed.");
+ if (isCol) //column name
+ {
+ isCol = false;
+ tokenUpper = token;
+ tokenUpper.ToUpper();
+ if (tokenUpper.Contains(" LIKE"))
+ {
+ isAppendEscape = true;
+ }
+ else
+ {
+ isAppendEscape = false;
+ }
+ r = inputExpr.Append(token);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");
+ }
+ else // value of the column
+ {
+ isCol = true;
+ r = inputExpr.Append("'");
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");
+ r = inputExpr.Append(token);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");
+ r = inputExpr.Append("'");
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");
+
+ if (isAppendEscape)
+ {
+ if (token.Contains("\\_") || token.Contains("\\%"))
+ {
+ r = inputExpr.Append("ESCAPE'\\' ");
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");
+ }
+ }
+ }
+ }
+
+ __inputExpr.Clear();
+ r = __inputExpr.Insert(inputExpr, 0);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string insert failed.");
+
+ return r;
+}
+
+//This function is to replace DateTime value(osp datetime type is string) which is string with int.(SLP dateTime column type is int)
+
+result
+_ContentSearchImpl::ReplaceDateTimeStringWithInt(void) const
+{
+ String delim = L"'"; //Delimeters is ' .
+ result r = E_SUCCESS;
+ bool isCol = true;
+ bool isConvertReq = false;
+ bool isBetweenExistsInDateTimeQuery = false;
+ String token;
+ String tokenUpper;
+ String inputExpr = __inputExpr;
+
+ if(!inputExpr.Contains("MEDIA_ADDED_TIME"))
+ {
+ return r;
+ }
+
+ // Create a StringTokenizer instance
+ StringTokenizer strTok(inputExpr, delim);
+
+ inputExpr.Clear();
+
+ while (strTok.HasMoreTokens())
+ {
+ r = strTok.GetNextToken(token);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "GetNextToken failed.");
+ if (isCol) //column name
+ {
+ isCol = false;
+ tokenUpper = token;
+ tokenUpper.ToUpper();
+ if(isBetweenExistsInDateTimeQuery)
+ {
+ isBetweenExistsInDateTimeQuery = false;
+ isConvertReq = true;
+ }
+ else
+ {
+ if (tokenUpper.Contains("MEDIA_ADDED_TIME"))
+ {
+ if (tokenUpper.Contains("BETWEEN"))
+ {
+ isBetweenExistsInDateTimeQuery = true;
+ }
+ isConvertReq = true;
+ }
+ else
+ {
+ isConvertReq = false;
+ }
+ }
+
+ r = inputExpr.Append(token);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "string append failed.");
+ }
+ else // value of the column
+ {
+ isCol = true;
+ r = inputExpr.Append("'");
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "string append failed.");
+
+ if (isConvertReq)
+ {
+ Tizen::Base::DateTime dt;
+ r = Tizen::Base::DateTime::Parse(token, dt);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "Failed to parse DateTime.");
+
+ int year = dt.GetYear();
+ int month = dt.GetMonth();
+ int day = dt.GetDay();
+ int hour = dt.GetHour();
+ int minute = dt.GetMinute();
+ int second = dt.GetSecond();
+
+ time_t rawTime;
+ struct tm* timeInfo;
+
+ time(&rawTime);
+ timeInfo = localtime(&rawTime);
+ timeInfo->tm_year = year - 1900;
+ timeInfo->tm_mon = month - 1;
+ timeInfo->tm_mday = day;
+ timeInfo->tm_hour = hour;
+ timeInfo->tm_min = minute;
+ timeInfo->tm_sec = second;
+
+ time_t seconds = mktime(timeInfo);
+ SysTryReturnResult(NID_CNT, seconds != -1, E_INVALID_ARG, "Failed to convert DateTime to broken-down time.");
+
+ long long ticksInSeconds = (long long)seconds;
+
+ r = inputExpr.Append(ticksInSeconds);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "string append failed.");
+ }
+ else
+ {
+ r = inputExpr.Append(token);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "string append failed.");
+ }
+
+ r = inputExpr.Append("'");
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "string append failed.");
+ }
+ }
+
+ __inputExpr.Clear();
+ r = __inputExpr.Insert(inputExpr, 0);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "string insert failed.");
+
+ return r;
+}
+
+// CONTENT_TYPE_OTHER and CONTENT_TYPE_IMAGE (0 - 13 ) are valid columns
+// CONTENT_TYPE_VIDEO (0 - 16 ) are valid columns
+// CONTENT_TYPE_ALL and CONTENT_TYPE_VIDEO (0 - 18 ) are valid columns
+// This functions checks for invalid column in the given input string (only allowed columns should be used by content type other wise
+// E_INVALID_ARG is returned)
+// StringTokenizer is used to parse input expression, by using delimater "'", to differentiate column and value.
+// As values may also contain column names
+// Ex: 1. where author = syam_author_01 2. where album = jalsa_album_name_01.
+
+result
+_ContentSearchImpl::CheckInvalidColumnInQuery(void) const
+{
+ result r = E_SUCCESS;
+ int tokenNo = 0;
+ String delim = L"'"; //Delimeters is ' .
+ bool isColReplaceReq = true;
+ String token;
+ String inputExpr = __inputExpr;
+
+ // Create a StringTokenizer instance
+ StringTokenizer strTok(inputExpr, delim);
+
+ inputExpr.Clear();
+
+ while (strTok.HasMoreTokens())
+ {
+ r = strTok.GetNextToken(token);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "strTok GetNextToken failed.");
+
+ SysLog(NID_CNT, "In CheckInvalidColumnInQuery token[%d] = %ls", ++tokenNo, token.GetPointer());
+
+ if (isColReplaceReq)
+ {
+ isColReplaceReq = false;
+ r = inputExpr.Append(token);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");
+ token.ToUpper();
+ switch (__contentType)
+ {
+ case CONTENT_TYPE_OTHER:
+ //fall through
+ case CONTENT_TYPE_IMAGE:
+ if ((token.Contains("TITLE")) || (token.Contains("ARTIST")) || (token.Contains("GENRE")))
+ {
+ SysLog(NID_CNT, "Title or Artist or Genre are not valid cloumns for this content type");
+ return E_INVALID_ARG;
+ }
+ //fall through
+ case CONTENT_TYPE_VIDEO:
+ if ((token.Contains("COMPOSER")) || (token.Contains("ALBUM")))
+ {
+ SysLog(NID_CNT, "Composer or Album are not valid cloumns for this content type");
+ return E_INVALID_ARG;
+ }
+ break;
+ default:
+ break;
+ }
+ }
+ else
+ {
+ isColReplaceReq = true;
+ r = inputExpr.Append("'");
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");
+ r = inputExpr.Append(token);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");
+ r = inputExpr.Append("'");
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");
+ }
+ }
+ return r;
+}
+
+// It replaces native column name with core column name.
+// StringTokenizer is used to parse input expression, by using delimiter "'", to differentiate column and value.
+// As values may also contain column names
+// Only column names are replaced but not values(values may contain column names)
+// Ex: 1. where author = syam_author_01 2. where album = jalsa_album_name_01.
+
+result
+_ContentSearchImpl::ReplaceString(String ospColumnName, String slpColumnName) const
+{
+ String delim = L"'"; //Delimiters is ' .
+ result r = E_SUCCESS;
+ bool isColReplaceReq = true;
+ String token;
+ String inputExpr = __inputExpr;
+
+ // Create a StringTokenizer instance
+ StringTokenizer strTok(inputExpr, delim);
+
+ inputExpr.Clear();
+
+ while (strTok.HasMoreTokens())
+ {
+ r = strTok.GetNextToken(token); // Osp, StringTokenizer, Sample, code
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string GetNextToken() failed.");
+ if (isColReplaceReq) //column name
+ {
+ isColReplaceReq = false;
+ r = token.Replace(ospColumnName, slpColumnName);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string replace() failed.");
+ r = inputExpr.Append(token);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");
+ }
+ else // value of the column
+ {
+ isColReplaceReq = true;
+ r = inputExpr.Append("'");
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");
+ r = inputExpr.Append(token);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");
+ r = inputExpr.Append("'");
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string append failed.");
+ }
+ }
+ __inputExpr.Clear();
+ r = __inputExpr.Insert(inputExpr, 0);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, E_SYSTEM, "string insert() failed.");
+
+ return r;
+}
+
+// Returns list of search result for the given expression and content type.
+Collection::IList*
+_ContentSearchImpl::SearchN(int pageNo, int countPerPage, int& totalPageCount, int& totalCount, const String& whereExpr, const String& sortColumn, SortOrder sortOrder) const
+{
+ SysLog(NID_CNT, "pageNo = %d, countPerPage = %d, whereExpr = %ls", pageNo, countPerPage, whereExpr.GetPointer());
+
+ ClearLastResult();
+
+ result r = E_SUCCESS;
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+ int offset = 0;
+
+ __inputColumnName.Clear();
+ __inputExpr.Clear();
+ __inputColumnName = sortColumn;
+ __inputSortOrder = sortOrder;
+ totalPageCount = 0;
+ totalCount = 0;
+
+ if (!whereExpr.IsEmpty()) // copy whereExpr if not empty to class variable __inputExpr
+ {
+ r = __inputExpr.Append(whereExpr);
+ SysTryReturn(NID_CNT, r == E_SUCCESS, NULL, r, "[%s] __inputExpr.Append Failed as whereExpr is not empty.", GetErrorMessage(r));
+
+ r = ReplaceOspColumnNameWithSlp();
+ SysTryReturn(NID_CNT, r == E_SUCCESS, NULL, r, "[%s] ReplaceOspColumnNameWithSlp for InputExpr Failed.", GetErrorMessage(r));
+
+ SysLog(NID_CNT, "After replace __inputExpr = %ls", __inputExpr.GetPointer());
+ }
+ if ((__inputColumnName.IsEmpty()) && ((__inputSortOrder == SORT_ORDER_ASCENDING) || (__inputSortOrder == SORT_ORDER_DESCENDING)))
+ {
+ SysLog(NID_CNT, "sort column name is empty and sort oder is not none. so,E_INVALID_ARG occured.");
+ SetLastResult(E_INVALID_ARG);
+ return null;
+ }
+ else
+ {
+ std::unique_ptr<ArrayList, AllElementsDeleter> pFinalOutList(new (std::nothrow) ArrayList());
+ SysTryReturn(NID_CNT, pFinalOutList.get() != null, NULL, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Failed to construct ArrayList.");
+
+ r = pFinalOutList->Construct();
+ SysTryReturn(NID_CNT, !IsFailed(r), NULL, r, "[%s] Failed to construct ArrayList.", GetErrorMessage(r));
+
+ __pFinalOutList = std::move(pFinalOutList);
+
+ r = CreateQueryFilter(true);
+ SysTryReturn(NID_CNT, !IsFailed(r), NULL, r, "[%s] Failed to perform CreateQueryFilter operation.", GetErrorMessage(r));
+
+ ret = media_info_get_media_count_from_db(__pFilterHandle.get(), &totalCount);
+ r = MapCoreErrorToNativeResult(ret);
+ SysTryReturn(NID_CNT, r == E_SUCCESS , NULL, r, "[%s] Failed to perform media_info_get_media_count_from_db operation.", GetErrorMessage(r));
+
+ SysLog(NID_CNT, "totalCount is [%d] for media_info_get_media_count_from_db", totalCount);
+
+ if (totalCount > 0)
+ {
+ if ((totalCount % countPerPage) == 0)
+ {
+ totalPageCount = totalCount / countPerPage;
+ }
+ else
+ {
+ totalPageCount = (totalCount / countPerPage) + 1;
+ }
+
+ SysTryReturn(NID_CNT, ((pageNo >= 1) && (pageNo <= totalPageCount)) , NULL, E_INVALID_ARG, "[E_INVALID_ARG] (pageNo < 1) || (pageNo > totalPageCount).");
+
+ offset = (pageNo * countPerPage) - countPerPage;
+
+ SysLog(NID_CNT, " SearchN totalCount [%d] totalPageCount[%d] __countPerPage[%d] __pageNo[%d] offset[%d]",
+ totalCount, totalPageCount, countPerPage, pageNo, offset);
+
+ ret = media_filter_set_offset(__pFilterHandle.get(), offset, countPerPage);
+ r = MapCoreErrorToNativeResult(ret);
+ SysTryReturn(NID_CNT, r == E_SUCCESS, NULL, r,
+ "[%s] Failed to perform media_filter_set_offset operation.", GetErrorMessage(r));
+
+ r = ExecuteAndFillFinalOutList();
+ SysTryReturn(NID_CNT, r == E_SUCCESS, NULL, E_SYSTEM, "[E_SYSTEM] ExecuteAndFillFinalOutList Failed.");
+ }
+ else if (pageNo > 1)
+ {
+ SysLogException(NID_CNT, E_INVALID_ARG, "[%s] (pageNo > 1) and (totalcount = 0).", GetErrorMessage(E_INVALID_ARG));
+
+ return null;
+ }
+ }
+ SetLastResult(r);
+ return __pFinalOutList.release();
+}
+
+// Fills final result list
+result
+_ContentSearchImpl::ExecuteAndFillFinalOutList(void) const
+{
+ SysLog(NID_CNT, "Enter\n");
+
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+ result r = E_SUCCESS;
+
+ std::unique_ptr<GList, SearchGListDeleter> pItemList;
+ GList* pTemp = NULL;
+ std::unique_ptr<media_info_s, SearchMediaHandleDeleter> pMediaHandle;
+
+ std::unique_ptr<ImageContentInfo> pImageContentInfo;
+ std::unique_ptr<AudioContentInfo> pAudioContentInfo;
+ std::unique_ptr<VideoContentInfo> pVideoContentInfo;
+ std::unique_ptr<OtherContentInfo> pOtherContentInfo;
+
+ _ImageContentInfoImpl* pImageContentInfoImpl = null;
+ _AudioContentInfoImpl* pAudioContentInfoImpl = null;
+ _VideoContentInfoImpl* pVideoContentInfoImpl = null;
+ _OtherContentInfoImpl* pOtherContentInfoImpl = null;
+
+ std::unique_ptr<ContentSearchResult> pContentSearchResult;
+
+ pTemp = pItemList.get();
+
+ ret = media_info_foreach_media_from_db(__pFilterHandle.get(), MediaItemCb, &pTemp);
+ r = MapCoreErrorToNativeResult(ret);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "Failed to perform media_info_foreach_media_from_db operation.");
+
+ SysTryReturnResult(NID_CNT, pTemp != NULL, r, "media_info_foreach_media_from_db pTemp is null.");
+
+ media_content_type_e mediaType = MEDIA_CONTENT_TYPE_OTHERS;
+
+ for (int idx = 0; idx < (int)g_list_length(pTemp); idx++)
+ {
+ pMediaHandle.reset(static_cast<media_info_h>(g_list_nth_data(pTemp, idx)));
+
+ ret = media_info_get_media_type(pMediaHandle.get(), &mediaType);
+ r = MapCoreErrorToNativeResult(ret);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform media_info_get_media_type.");
+
+ std::unique_ptr<char, UtilCharDeleter> pMediaPath;
+ char* pTempPath = null;
+
+ ret = media_info_get_file_path(pMediaHandle.get(), &pTempPath);
+ r = MapCoreErrorToNativeResult(ret);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform media_info_get_file_path operation.");
+
+ pMediaPath.reset(pTempPath);
+ String contentPath(pMediaPath.get());
+ String changedPath(contentPath);
+
+ // If the api version is 2.0, the content path has to be changed.
+ if (_AppInfo::GetApiVersion() == _API_VERSION_2_0 && _AppInfo::IsOspCompat())
+ {
+ r = _FileImpl::ConvertPhysicalToVirtualPath(contentPath, changedPath);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), E_INVALID_ARG,
+ "[%s] Failed to convert physical path to virtual path.", GetErrorMessage(E_INVALID_ARG));
+ }
+
+ switch (mediaType)
+ {
+ case MEDIA_CONTENT_TYPE_OTHERS:
+ pOtherContentInfo = std::unique_ptr<OtherContentInfo>(new (std::nothrow) OtherContentInfo);
+ SysTryReturnResult(NID_CNT, pOtherContentInfo.get() != null, E_OUT_OF_MEMORY, "Failed to create pOtherContentInfo.");
+
+ r = pOtherContentInfo->Construct(&changedPath);
+ r = ConvertErrorToResult(r);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform Construct operation to OtherContentInfo.");
+
+ pOtherContentInfoImpl = null;
+ pOtherContentInfoImpl = _OtherContentInfoImpl::GetInstance(*(pOtherContentInfo.get()));
+ SysTryReturnResult(NID_CNT, pOtherContentInfoImpl != null, E_OUT_OF_MEMORY, "Failed to assign operation to pOtherContentInfoImpl.");
+
+ r = _ContentUtility::FillContentData(pMediaHandle.get(), pOtherContentInfoImpl);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform FillContentData operation.");
+
+ _ContentInfoHelper::SetContentInfoImpl(pOtherContentInfo.get(), pOtherContentInfoImpl);
+
+ pContentSearchResult = std::unique_ptr<ContentSearchResult>(new (std::nothrow) ContentSearchResult);
+ SysTryReturnResult(NID_CNT, pContentSearchResult.get() != null, E_OUT_OF_MEMORY, "Failed to create pContentSearchResult.");
+
+ pContentSearchResult->SetContentType(CONTENT_TYPE_OTHER);
+ pContentSearchResult->SetContentInfo(pOtherContentInfo.release());
+
+ // Shallow copy, adds just the pointer: not the element
+ r = __pFinalOutList->Add(*(pContentSearchResult.release()));
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform Add operation for ArrayList.");
+
+ break;
+ case MEDIA_CONTENT_TYPE_IMAGE:
+ pImageContentInfo = std::unique_ptr<ImageContentInfo>(new (std::nothrow) ImageContentInfo);
+ SysTryReturnResult(NID_CNT, pImageContentInfo.get() != null, E_OUT_OF_MEMORY, "Failed to create pImageContentInfo.");
+
+ r = pImageContentInfo->Construct(&changedPath);
+ r = ConvertErrorToResult(r);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform Construct operation to ImageContentInfo.");
+
+ pImageContentInfoImpl = null;
+ pImageContentInfoImpl = _ImageContentInfoImpl::GetInstance(*(pImageContentInfo.get()));
+ SysTryReturnResult(NID_CNT, pImageContentInfoImpl != null, E_OUT_OF_MEMORY, "Failed to assign operation to pImageContentInfoImpl.");
+
+ r = _ContentUtility::FillContentData(pMediaHandle.get(), pImageContentInfoImpl);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform FillContentData operation.");
+
+ r = _ContentUtility::FillImageContentData(pMediaHandle.get(), pImageContentInfoImpl);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform GetDataFromImageTable operation.");
+
+ _ContentInfoHelper::SetContentInfoImpl(pImageContentInfo.get(), pImageContentInfoImpl);
+
+ pContentSearchResult = std::unique_ptr<ContentSearchResult>(new (std::nothrow) ContentSearchResult);
+ SysTryReturnResult(NID_CNT, pContentSearchResult.get() != null, E_OUT_OF_MEMORY, "Failed to create pContentSearchResult.");
+
+ pContentSearchResult->SetContentType(CONTENT_TYPE_IMAGE);
+ pContentSearchResult->SetContentInfo(pImageContentInfo.release());
+
+ // Shallow copy, adds just the pointer: not the element
+ r = __pFinalOutList->Add(*(pContentSearchResult.release()));
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform Add operation for ArrayList.");
+
+ break;
+ case MEDIA_CONTENT_TYPE_MUSIC:
+ //fall through
+ case MEDIA_CONTENT_TYPE_SOUND:
+ pAudioContentInfo = std::unique_ptr<AudioContentInfo>(new (std::nothrow) AudioContentInfo);
+ SysTryReturnResult(NID_CNT, pAudioContentInfo.get() != null, E_OUT_OF_MEMORY, "Failed to create pAudioContentInfo.");
+
+ r = pAudioContentInfo->Construct(&changedPath);
+ r = ConvertErrorToResult(r);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform Construct operation to AudioContentInfo.");
+
+ pAudioContentInfoImpl = null;
+ pAudioContentInfoImpl = _AudioContentInfoImpl::GetInstance(*(pAudioContentInfo.get()));
+ SysTryReturnResult(NID_CNT, pAudioContentInfoImpl != null, E_OUT_OF_MEMORY, "Failed to assign operation to pAudioContentInfoImpl.");
+
+ r = _ContentUtility::FillContentData(pMediaHandle.get(), pAudioContentInfoImpl);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform FillContentData operation.");
+
+ r = _ContentUtility::FillAudioContentData(pMediaHandle.get(), pAudioContentInfoImpl);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform FillAudioContentData operation.");
+
+ _ContentInfoHelper::SetContentInfoImpl(pAudioContentInfo.get(), pAudioContentInfoImpl);
+
+ pContentSearchResult = std::unique_ptr<ContentSearchResult>(new (std::nothrow) ContentSearchResult);
+ SysTryReturnResult(NID_CNT, pContentSearchResult.get() != null, E_OUT_OF_MEMORY, "Failed to create pContentSearchResult.");
+
+ pContentSearchResult->SetContentType(CONTENT_TYPE_AUDIO);
+ pContentSearchResult->SetContentInfo(pAudioContentInfo.release());
+
+ // Shallow copy, adds just the pointer: not the element
+ r = __pFinalOutList->Add(*(pContentSearchResult.release()));
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform Add operation for ArrayList.");
+
+ break;
+ case MEDIA_CONTENT_TYPE_VIDEO:
+ pVideoContentInfo = std::unique_ptr<VideoContentInfo>(new (std::nothrow) VideoContentInfo);
+ SysTryReturnResult(NID_CNT, pVideoContentInfo.get() != null, E_OUT_OF_MEMORY, "Failed to create pVideoContentInfo.");
+
+ r = pVideoContentInfo->Construct(&changedPath);
+ r = ConvertErrorToResult(r);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform Construct operation to VideoContentInfo.");
+
+ pVideoContentInfoImpl = null;
+ pVideoContentInfoImpl = _VideoContentInfoImpl::GetInstance(*(pVideoContentInfo.get()));
+ SysTryReturnResult(NID_CNT, pVideoContentInfoImpl != null, E_OUT_OF_MEMORY, "Failed to assign operation to pVideoContentInfoImpl.");
+
+ r = _ContentUtility::FillContentData(pMediaHandle.get(), pVideoContentInfoImpl);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform FillContentData operation.");
+
+ r = _ContentUtility::FillVideoContentData(pMediaHandle.get(), pVideoContentInfoImpl);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform FillVideoContentData operation.");
+
+ _ContentInfoHelper::SetContentInfoImpl(pVideoContentInfo.get(), pVideoContentInfoImpl);
+
+ pContentSearchResult = std::unique_ptr<ContentSearchResult>(new (std::nothrow) ContentSearchResult);
+ SysTryReturnResult(NID_CNT, pContentSearchResult.get() != null, E_OUT_OF_MEMORY, "Failed to create pContentSearchResult.");
+
+ pContentSearchResult->SetContentType(CONTENT_TYPE_VIDEO);
+ pContentSearchResult->SetContentInfo(pVideoContentInfo.release());
+
+ // Shallow copy, adds just the pointer: not the element
+ r = __pFinalOutList->Add(*(pContentSearchResult.release()));
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform Add operation for ArrayList.");
+
+ break;
+ default:
+ break;
+ }
+ }
+ return r;
+}
+
+// returns given column value list in the requested order
+Collection::IList*
+_ContentSearchImpl::GetValueListN(const String& sortColumn, SortOrder sortOrder)
+{
+ SysLog(NID_CNT, "inputColumn = %ls", sortColumn.GetPointer());
+ ClearLastResult();
+
+ result r = E_SUCCESS;
+ int colIndex = 0;
+ int maxCols = 0;
+
+ __inputColumnName.Clear();
+ __inputExpr.Clear();
+
+ __inputColumnName = sortColumn;
+ __inputSortOrder = sortOrder;
+
+ String ospColumnName(L"");
+ String slpColumnName(L"");
+
+ String columnName(__inputColumnName);
+
+ if ((__inputColumnName.IsEmpty()) && ((__inputSortOrder == SORT_ORDER_ASCENDING) || (__inputSortOrder == SORT_ORDER_DESCENDING)))
+ {
+ SysLog(NID_CNT, "sort column name is empty and sort oder is not none. so,E_INVALID_ARG occured.");
+ SetLastResult(E_INVALID_ARG);
+ return null;
+ }
+ else
+ {
+ std::unique_ptr<ArrayList, AllElementsDeleter> pFinalOutList(new (std::nothrow) ArrayList());
+ SysTryReturn(NID_CNT, pFinalOutList.get() != null, NULL, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Failed to construct ArrayList.");
+
+ r = pFinalOutList->Construct();
+ SysTryReturn(NID_CNT, !IsFailed(r), NULL, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Failed to construct ArrayList.");
+
+ __pFinalOutList = std::move(pFinalOutList);
+
+ switch (__contentType)
+ {
+ case CONTENT_TYPE_OTHER:
+ //fall through
+ case CONTENT_TYPE_IMAGE:
+ maxCols = MAX_QUERY_COLUMNS_FOR_IMAGE_OTHERS;
+ break;
+ case CONTENT_TYPE_VIDEO:
+ maxCols = MAX_QUERY_COLUMNS_FOR_VIDEO;
+ break;
+ case CONTENT_TYPE_AUDIO:
+ //fall through
+ case CONTENT_TYPE_ALL:
+ maxCols = MAX_QUERY_COLUMNS;
+ break;
+ default:
+ break;
+ }
+
+ for (colIndex = 0; colIndex < maxCols; colIndex++)
+ {
+ ospColumnName.Clear();
+ slpColumnName.Clear();
+
+ ospColumnName = dbfieldinfo[colIndex].dbFieldOspName ;
+ slpColumnName = dbfieldinfo[colIndex].dbFieldSlpName ;
+
+ ospColumnName.ToUpper();
+ columnName.ToUpper();
+ if (columnName == ospColumnName)
+ {
+ r = FillColumnsList(colIndex);
+ SysTryReturn(NID_CNT, r == E_SUCCESS, NULL, r, "[%s] FillColumnsList Failed.", GetErrorMessage(r));
+ break;
+ }
+ }
+ if (colIndex == maxCols)
+ {
+ SysLogException(NID_CNT, E_INVALID_ARG, "[%s] The column is invalid.", GetErrorMessage(E_INVALID_ARG));
+
+ return null;
+ }
+ }
+ SetLastResult(r);
+ return __pFinalOutList.release();
+}
+
+// returns given column value list in the requested order
+Collection::IList*
+_ContentSearchImpl::GetValueListN(int pageNo, int countPerPage, int& totalPageCount, int& totalCount, const String& sortColumn, SortOrder sortOrder) const
+{
+ SysLog(NID_CNT, "pageNo = %d, countPerPage = %d, inputColumn = %ls", pageNo, countPerPage, sortColumn.GetPointer());
+
+ ClearLastResult();
+
+ result r = E_SUCCESS;
+ int colIndex = 0;
+ int maxCols = 0;
+
+ __inputColumnName.Clear();
+ __inputExpr.Clear();
+
+ __inputColumnName = sortColumn;
+ __inputSortOrder = sortOrder;
+
+ String ospColumnName(L"");
+ String slpColumnName(L"");
+
+ String columnName(__inputColumnName);
+
+ if ((__inputColumnName.IsEmpty()) && ((__inputSortOrder == SORT_ORDER_ASCENDING) || (__inputSortOrder == SORT_ORDER_DESCENDING)))
+ {
+ SysLog(NID_CNT, "sort column name is empty and sort oder is not none. so,E_INVALID_ARG occured.");
+ SetLastResult(E_INVALID_ARG);
+ return null;
+ }
+ else
+ {
+ std::unique_ptr<ArrayList, AllElementsDeleter> pFinalOutList(new (std::nothrow) ArrayList());
+ SysTryReturn(NID_CNT, pFinalOutList.get() != null, NULL, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Failed to construct ArrayList.");
+
+ r = pFinalOutList->Construct();
+ SysTryReturn(NID_CNT, !IsFailed(r), NULL, r, "[%s] Failed to construct ArrayList.", GetErrorMessage(r));
+
+ __pFinalOutList = std::move(pFinalOutList);
+
+ switch (__contentType)
+ {
+ case CONTENT_TYPE_OTHER:
+ //fall through
+ case CONTENT_TYPE_IMAGE:
+ maxCols = MAX_QUERY_COLUMNS_FOR_IMAGE_OTHERS;
+ break;
+ case CONTENT_TYPE_VIDEO:
+ maxCols = MAX_QUERY_COLUMNS_FOR_VIDEO;
+ break;
+ case CONTENT_TYPE_AUDIO:
+ //fall through
+ case CONTENT_TYPE_ALL:
+ maxCols = MAX_QUERY_COLUMNS;
+ break;
+ default:
+ break;
+ }
+
+ for (colIndex = 0; colIndex < maxCols; colIndex++)
+ {
+ ospColumnName.Clear();
+ slpColumnName.Clear();
+
+ ospColumnName = dbfieldinfo[colIndex].dbFieldOspName ;
+ slpColumnName = dbfieldinfo[colIndex].dbFieldSlpName ;
+
+ ospColumnName.ToUpper();
+ columnName.ToUpper();
+ if (columnName == ospColumnName)
+ {
+ r = FillColumnsList(pageNo, countPerPage, totalPageCount, totalCount, colIndex);
+ SysTryReturn(NID_CNT, r == E_SUCCESS, NULL, r, "[%s] FillColumnsList Failed.", GetErrorMessage(r));
+ break;
+ }
+ }
+ if (colIndex == maxCols)
+ {
+ SysLogException(NID_CNT, E_INVALID_ARG, "[%s] The column is invalid.", GetErrorMessage(E_INVALID_ARG));
+
+ return null;
+ }
+ }
+ SetLastResult(r);
+ return __pFinalOutList.release();
+}
+
+// prepares query expression to be used in group api. colIndex is mapped to actual group value.
+media_group_e
+_ContentSearchImpl::GetIndexAndCreateQueryExp(int colIndex) const
+{
+ media_group_e groupIndex = MEDIA_CONTENT_GROUP_DISPLAY_NAME;;
+ switch (colIndex)
+ {
+ case 0://"ContentType", "MEDIA_TYPE"
+ groupIndex = MEDIA_CONTENT_GROUP_TYPE;
+ __inputExpr = "MEDIA_TYPE IS NOT NULL";
+ break;
+ case 1://"ContentFileName", "MEDIA_DISPLAY_NAME"
+ groupIndex = MEDIA_CONTENT_GROUP_DISPLAY_NAME;
+ __inputExpr = "MEDIA_DISPLAY_NAME IS NOT NULL";
+ break;
+ case 2://"ContentName", "MEDIA_CONTENT_NAME"
+ groupIndex = MEDIA_CONTENT_GROUP_CONTENT_NAME;
+ __inputExpr = "MEDIA_CONTENT_NAME IS NOT NULL";
+ break;
+ case 3://"Category", "MEDIA_CATEGORY"
+ groupIndex = MEDIA_CONTENT_GROUP_CATEGORY;
+ __inputExpr = "MEDIA_CATEGORY IS NOT NULL";
+ break;
+ case 4://"Author", "MEDIA_AUTHOR"
+ groupIndex = MEDIA_CONTENT_GROUP_AUTHOR;
+ __inputExpr = "MEDIA_AUTHOR IS NOT NULL";
+ break;
+ case 5://"keyword", "MEDIA_KEYWORD"
+ groupIndex = MEDIA_CONTENT_GROUP_KEYWORD;
+ __inputExpr = "MEDIA_KEYWORD IS NOT NULL";
+ break;
+ case 6://"Provider", "MEDIA_PROVIDER"
+ groupIndex = MEDIA_CONTENT_GROUP_PROVIDER;
+ __inputExpr = "MEDIA_PROVIDER IS NOT NULL";
+ break;
+ case 7://"Rating", "MEDIA_AGE_RATING"
+ groupIndex = MEDIA_CONTENT_GROUP_AGE_RATING;
+ __inputExpr = "MEDIA_AGE_RATING IS NOT NULL";
+ break;
+ case 8://"LocationTag", "MEDIA_LOCATION_TAG"
+ groupIndex = MEDIA_CONTENT_GROUP_LOCATION_TAG;
+ __inputExpr = "MEDIA_LOCATION_TAG IS NOT NULL";
+ break;
+ case 9://"ContentSize", "MEDIA_SIZE"
+ groupIndex = MEDIA_CONTENT_GROUP_SIZE;
+ __inputExpr = "MEDIA_SIZE IS NOT NULL";
+ break;
+ case 10://"DateTime", "MEDIA_ADDED_TIME"
+ groupIndex = MEDIA_CONTENT_GROUP_ADDED_TIME;
+ __inputExpr = "MEDIA_ADDED_TIME IS NOT NULL";
+ break;
+ case 11://"Latitude", "MEDIA_LATITUDE"
+ groupIndex = MEDIA_CONTENT_GROUP_LATITUDE;
+ __inputExpr = "MEDIA_LATITUDE IS NOT NULL";
+ break;
+ case 12://"Longitude", "MEDIA_LONGITUDE"
+ groupIndex = MEDIA_CONTENT_GROUP_LONGITUDE;
+ __inputExpr = "MEDIA_LONGITUDE IS NOT NULL";
+ break;
+ case 13://"Altitude", "MEDIA_ALTITUDE"
+ groupIndex = MEDIA_CONTENT_GROUP_ALTITUDE;
+ __inputExpr = "MEDIA_ALTITUDE IS NOT NULL";
+ break;
+ case 14://"Title", "MEDIA_TITLE"
+ groupIndex = MEDIA_CONTENT_GROUP_TITLE;
+ __inputExpr = "MEDIA_TITLE IS NOT NULL";
+ break;
+ case 15://"Artist", "MEDIA_ARTIST"
+ groupIndex = MEDIA_CONTENT_GROUP_ARTIST;
+ __inputExpr = "MEDIA_ARTIST IS NOT NULL";
+ break;
+ case 16://"Genre", "MEDIA_GENRE"
+ groupIndex = MEDIA_CONTENT_GROUP_GENRE;
+ __inputExpr = "MEDIA_GENRE IS NOT NULL";
+ break;
+ case 17://"Year", "MEDIA_YEAR"
+ groupIndex = MEDIA_CONTENT_GROUP_YEAR;
+ __inputExpr = "MEDIA_YEAR IS NOT NULL";
+ break;
+ case 18://"Composer", "MEDIA_COMPOSER"
+ groupIndex = MEDIA_CONTENT_GROUP_COMPOSER;
+ __inputExpr = "MEDIA_COMPOSER IS NOT NULL";
+ break;
+ case 19://"Album", "MEDIA_ALBUM"
+ __inputExpr = "MEDIA_ALBUM IS NOT NULL";
+ break;
+ default:
+ break;
+ }
+ return groupIndex;
+}
+
+// Fills given column value list and destroys filter handle
+result
+_ContentSearchImpl::FillColumnsList(int colIndex) const
+{
+ result r = E_SUCCESS;
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+ int totalCount = 0;
+ media_group_e groupIndex = GetIndexAndCreateQueryExp(colIndex);
+
+ r = CreateQueryFilter(true);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "CreateQueryFilter Failed.");
+
+ if (colIndex == ALBUM_COLUMN_NUM)
+ {
+ ret = media_album_get_album_count_from_db(__pFilterHandle.get(), &totalCount);
+ }
+ else
+ {
+ ret = media_group_get_group_count_from_db(__pFilterHandle.get(), groupIndex, &totalCount);
+ }
+ r = MapCoreErrorToNativeResult(ret);
+ SysTryReturnResult(NID_CNT, ret == MEDIA_CONTENT_ERROR_NONE, r, "Failed to perform media_album/group count_from_db operation.");
+
+ SysLog(NID_CNT, "totalCount = %d for media_album/group count_from_db", totalCount);
+
+ if (totalCount > 0)
+ {
+ if (colIndex == ALBUM_COLUMN_NUM)
+ {
+ r = ExecuteAndFillAlbumValues();
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "ExecuteAndFillAlbumValues Failed.");
+ }
+ else
+ {
+ r = ExecuteAndFillGetValueListN(groupIndex, colIndex);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "ExecuteAndFillGetValueListN Failed.");
+ }
+ }
+ return r;
+}
+
+// prepares input expression to be sent for create filter and fills given column value list
+result
+_ContentSearchImpl::FillColumnsList(int pageNo, int countPerPage, int& totalPageCount, int& totalCount, int colIndex) const
+{
+ result r = E_SUCCESS;
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+ int offset = 0;
+ totalPageCount = 0;
+ totalCount = 0;
+ media_group_e groupIndex = GetIndexAndCreateQueryExp(colIndex);
+
+ r = CreateQueryFilter(true);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "CreateQueryFilter Failed.");
+
+ if (colIndex == ALBUM_COLUMN_NUM)
+ {
+ ret = media_album_get_album_count_from_db(__pFilterHandle.get(), &totalCount);
+ }
+ else
+ {
+ ret = media_group_get_group_count_from_db(__pFilterHandle.get(), groupIndex, &totalCount);
+ }
+ r = MapCoreErrorToNativeResult(ret);
+ SysTryReturnResult(NID_CNT, ret == MEDIA_CONTENT_ERROR_NONE, r, "Failed to perform media_album/group count_from_db operation.");
+
+ SysLog(NID_CNT, "totalCount = %d for media_album/group count_from_db", totalCount);
+
+ if (totalCount > 0)
+ {
+ if ((totalCount % countPerPage) == 0)
+ {
+ totalPageCount = totalCount / countPerPage;
+ }
+ else
+ {
+ totalPageCount = (totalCount / countPerPage) + 1;
+ }
+
+ SysTryReturnResult(NID_CNT, ((pageNo >= 1) && (pageNo <= totalPageCount)) , r, "(pageNo < 1) || (pageNo > totalPageCount).");
+
+ offset = (pageNo * countPerPage) - countPerPage;
+
+ SysLog(NID_CNT, "GetValueListN totalCount [%d] totalPageCount[%d] __countPerPage[%d] __pageNo[%d] offset[%d]",
+ totalCount, totalPageCount, countPerPage, pageNo, offset);
+
+ ret = media_filter_set_offset(__pFilterHandle.get(),offset,countPerPage);
+ r = MapCoreErrorToNativeResult(ret);
+ SysTryReturnResult(NID_CNT, ret == MEDIA_CONTENT_ERROR_NONE, r, "failed to perform media_filter_set_offset operation.");
+
+ if (colIndex == ALBUM_COLUMN_NUM)
+ {
+ r = ExecuteAndFillAlbumValues();
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "ExecuteAndFillAlbumValues Failed.");
+ }
+ else
+ {
+ r = ExecuteAndFillGetValueListN(groupIndex, colIndex);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "ExecuteAndFillGetValueListN Failed.");
+ }
+
+ }
+ else if (pageNo > 1)
+ {
+ SysLogException(NID_CNT, r = E_INVALID_ARG, "[%s] (pageNo > 1) and (totalcount = 0).", GetErrorMessage(E_INVALID_ARG));
+ }
+
+ return r;
+}
+
+// fills given column value list for GetValuelistN api
+result
+_ContentSearchImpl::ExecuteAndFillGetValueListN(media_group_e groupIndex, int colIndex) const
+{
+ SysLog(NID_CNT, "Enter\n");
+
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+ result r = E_SUCCESS;
+ result res = E_SUCCESS;
+ std::unique_ptr<GList, SearchGListDeleter> pItemList;
+ GList* pTemp = NULL;
+
+ std::unique_ptr<Object> pValue;
+
+ DateTime dateTime;
+
+ long long contentSize = 0;
+ long long addedTime = 0;
+
+ double dVal = 0;
+ char *pColumnVal = null;
+ int contentType = 0;
+
+ pTemp = pItemList.get();
+
+ ret = media_group_foreach_group_from_db(__pFilterHandle.get(), groupIndex, GroupItemCb, &pTemp);
+ r = MapCoreErrorToNativeResult(ret);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "Failed to perform media_group_foreach_group_from_db operation.");
+
+ SysTryReturnResult(NID_CNT, pTemp != NULL, r, "media_info_foreach_media_from_db pTemp is null.");
+
+ for (int idx = 0; idx < (int)g_list_length(pTemp); idx++)
+ {
+ SysLog(NID_CNT, "idx = %d and (int)g_list_length(pItemList) = %d", idx, (int)g_list_length(pTemp));
+
+ pColumnVal = (char *)g_list_nth_data(pTemp, idx);
+
+ String strColVal(pColumnVal);
+
+ _ContentUtility::DoSafeFree(pColumnVal);
+
+ SysLog(NID_CNT, "pColumnVal = %ls", strColVal.GetPointer());
+
+ switch (colIndex)
+ {
+ case 0://"ContentType", "MEDIA_TYPE"
+ if ((strColVal.CompareTo(L"Unknown") != 0) && (!strColVal.IsEmpty()))
+ {
+ res = Integer::Parse(strColVal, contentType);
+ SysTryLog(NID_CNT, res == E_SUCCESS, "[%s] Integer parse failed.", GetErrorMessage(res));
+ }
+ switch ((media_content_type_e)contentType)
+ {
+ case MEDIA_CONTENT_TYPE_OTHERS:
+ pValue.reset(new (std::nothrow) String(CONTENT_TYPE_OTHER));
+ SysLog(NID_CNT, "mediaType = CONTENT_TYPE_OTHER");
+ break;
+ case MEDIA_CONTENT_TYPE_IMAGE:
+ pValue.reset(new (std::nothrow) String(CONTENT_TYPE_IMAGE));
+ SysLog(NID_CNT, "mediaType = CONTENT_TYPE_IMAGE");
+ break;
+ case MEDIA_CONTENT_TYPE_SOUND:
+ //fall through
+ case MEDIA_CONTENT_TYPE_MUSIC:
+ pValue.reset(new (std::nothrow) String(CONTENT_TYPE_AUDIO));
+ SysLog(NID_CNT, "mediaType = CONTENT_TYPE_AUDIO");
+ break;
+ case MEDIA_CONTENT_TYPE_VIDEO:
+ pValue.reset(new (std::nothrow) String(CONTENT_TYPE_VIDEO));
+ SysLog(NID_CNT, "mediaType = CONTENT_TYPE_VIDEO");
+ break;
+ default:
+ break;
+ }
+ break;
+ case 1://"ContentFileName", "MEDIA_DISPLAY_NAME"
+ //fall through
+ case 2://"ContentName", "MEDIA_CONTENT_NAME"
+ //fall through
+ case 3://"Category", "MEDIA_CATEGORY"
+ //fall through
+ case 4://"Author", "MEDIA_AUTHOR"
+ //fall through
+ case 5://"keyword", "MEDIA_KEYWORD"
+ //fall through
+ case 6://"Provider", "MEDIA_PROVIDER"
+ //fall through
+ case 7://"Rating", "MEDIA_AGE_RATING"
+ //fall through
+ case 8://"LocationTag", "MEDIA_LOCATION_TAG"
+ //fall through
+ case 14://"Title", "MEDIA_TITLE"
+ //fall through
+ case 15://"Artist", "MEDIA_ARTIST"
+ //fall through
+ case 16://"Genre", "MEDIA_GENRE"
+ //fall through
+ case 17://"Year", "MEDIA_YEAR"
+ //fall through
+ case 18://"Composer", "MEDIA_COMPOSER"
+
+ pValue.reset(new (std::nothrow) String(strColVal));
+ break;
+
+ case 9://"ContentSize", "MEDIA_SIZE"
+ if ((strColVal.CompareTo(L"Unknown") != 0) && (!strColVal.IsEmpty()))
+ {
+ res = LongLong::Parse(strColVal, contentSize);
+ SysTryLog(NID_CNT, res == E_SUCCESS, "[%s] LongLong parse failed.", GetErrorMessage(res));
+ }
+
+ pValue.reset(new (std::nothrow) LongLong(contentSize));
+ break;
+ case 10://"DateTime", "MEDIA_ADDED_TIME"
+ if ((strColVal.CompareTo(L"Unknown") != 0) && (!strColVal.IsEmpty()))
+ {
+ res = LongLong::Parse(strColVal, addedTime);
+ SysTryLog(NID_CNT, res == E_SUCCESS, "[%s] LongLong parse failed.", GetErrorMessage(res));
+ }
+
+ res = dateTime.SetValue(1970, 1, 1);
+ SysTryLog(NID_CNT, res == E_SUCCESS, "[%s] dateTime.SetValue failed.", GetErrorMessage(res));
+
+ res = dateTime.AddSeconds(addedTime);
+ SysTryLog(NID_CNT, res == E_SUCCESS, "[%s] dateTime.AddSeconds failed.", GetErrorMessage(res));
+
+ SysLog(NID_CNT, "DateTime : %ls", dateTime.ToString().GetPointer());
+
+ pValue.reset(new (std::nothrow) DateTime(dateTime));
+
+ break;
+ case 11://"Latitude", "MEDIA_LATITUDE"
+ //fall through
+ case 12://"Longitude", "MEDIA_LONGITUDE"
+ //fall through
+ case 13://"Altitude", "MEDIA_ALTITUDE"
+ if ((strColVal.CompareTo(L"Unknown") != 0) && (!strColVal.IsEmpty()))
+ {
+ dVal = _LocalizedNumParser::ToDouble(strColVal, "C");
+ r = GetLastResult();
+ SysTryReturnResult(NID_CNT, !IsFailed(r), E_INVALID_ARG, "Failed to perform ToDouble operation.");
+ }
+ pValue.reset(new (std::nothrow) Double(dVal));
+ break;
+
+ case 19://"Album", "MEDIA_ALBUM"
+ break;
+ default:
+ break;
+ }
+ if (pValue.get() != NULL)
+ {
+ r = __pFinalOutList->Add(*(pValue.release()));
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "Failed to perform arraylist Add operation.");
+ }
+ }
+
+ return r;
+}
+
+result
+_ContentSearchImpl::ExecuteAndFillAlbumValues(void) const
+{
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+ result r = E_SUCCESS;
+ std::unique_ptr<GList, SearchGListDeleter> pItemList;
+ GList* pTemp = NULL;
+ std::unique_ptr<media_album_s, AlbumHandleDeleter> pAlbumHandle;
+ std::unique_ptr<media_album_s, AlbumHandleDeleter> pTempAlbumHandle;
+
+ char* pName = NULL;
+ std::unique_ptr<char, CharDeleter> pAlbumName;
+ std::unique_ptr< String > pValue;
+ int lastIndex = 0;
+
+ pTemp = pItemList.get();
+
+ ret = media_album_foreach_album_from_db(__pFilterHandle.get(), AlbumItemCb, &pTemp);
+ r = MapCoreErrorToNativeResult(ret);
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "Failed to perform media_album_foreach_album_from_db operation.");
+ SysTryReturnResult(NID_CNT, pTemp != NULL, r, "media_info_foreach_media_from_db pTemp is null.");
+
+ for (int idx = 0; idx < (int)g_list_length(pTemp); idx++)
+ {
+ pAlbumHandle.reset(static_cast<media_album_h>(g_list_nth_data(pTemp, idx)));
+ ret = media_album_get_name(pAlbumHandle.get(), &pName);
+ r = MapCoreErrorToNativeResult(ret);
+ SysTryReturnResult(NID_CNT, !IsFailed(r), r, "Failed to perform media_album_get_name.");
+
+ if (pName != NULL)
+ {
+ SysLog(NID_CNT, "pColumnVal = %s", pName);
+
+ pAlbumName.reset(pName);
+ pValue.reset(new (std::nothrow) String(pAlbumName.get()));
+ SysTryReturnResult(NID_CNT, pValue != NULL, E_OUT_OF_MEMORY, "media_info_foreach_media_from_db pTemp is null.");
+
+ if (idx == 0)
+ {
+ r = __pFinalOutList->Add(pValue.get());
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "Failed to perform arraylist Add operation.");
+ pValue.release();
+ }
+ else
+ {
+ String* pTempNameList(static_cast< String* >(__pFinalOutList->GetAt(lastIndex)));
+
+ if (pValue->CompareTo(*pTempNameList) != 0)
+ {
+ r = __pFinalOutList->Add(pValue.get());
+ SysTryReturnResult(NID_CNT, r == E_SUCCESS, r, "Failed to perform arraylist Add operation.");
+
+ pValue.release();
+ lastIndex++;
+ }
+ }
+ }
+ }
+
+ return r;
+}
+
+result
+_ContentSearchImpl::MapCoreErrorToNativeResult(int reason) const
+{
+ result r = E_SUCCESS;
+
+ switch (reason)
+ {
+ case MEDIA_CONTENT_ERROR_NONE:
+ r = E_SUCCESS;
+ break;
+
+ case MEDIA_CONTENT_ERROR_INVALID_PARAMETER:
+ r = E_INVALID_ARG;
+ SysLog(NID_CNT, "MEDIA_CONTENT_ERROR_INVALID_PARAMETER");
+ break;
+
+ case MEDIA_CONTENT_ERROR_DB_FAILED:
+ r = E_SYSTEM;
+ SysLog(NID_CNT, "MEDIA_CONTENT_ERROR_DB_FAILED");
+ break;
+
+ case MEDIA_CONTENT_ERROR_OUT_OF_MEMORY:
+ r = E_OUT_OF_MEMORY;
+ SysLog(NID_CNT, "MEDIA_CONTENT_ERROR_OUT_OF_MEMORY");
+ break;
+
+ default:
+ SysLog(NID_CNT, "default");
+ r = E_SYSTEM;
+ break;
+ }
+ return r;
+}
+
+result
+_ContentSearchImpl::ConvertErrorToResult(result res) const
+{
+ result r = E_SUCCESS;
+
+ switch (res)
+ {
+ case E_FILE_NOT_FOUND:
+ // Fall through
+ case E_IO:
+ r = E_SYSTEM;
+ break;
+
+ default:
+ r = res;
+ break;
+ }
+ return r;
+}
+
+// Callback function registered to each media info details
+// all items are appended to the list
+bool
+MediaItemCb(media_info_h media, void* pUserdata)
+{
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+ media_info_h new_media = NULL;
+ ret = media_info_clone(&new_media, media);
+ SysTryLog(NID_CNT, ret == MEDIA_CONTENT_ERROR_NONE, "[E_SYSTEM] Failed to perform media_info_clone");
+
+ GList** pList = (GList**)pUserdata;
+ *pList = g_list_append(*pList, new_media);
+
+ return true;
+}
+
+// Callback function registered for column values
+// all items are appended to the list
+bool
+GroupItemCb(const char* pGroupName, void* pUserdata)
+{
+ char* pGrpName = strdup(pGroupName);
+ GList** pList = (GList**)pUserdata;
+ *pList = g_list_append(*pList, pGrpName);
+
+ return true;
+}
+
+// Callback function registered to each media info details
+// all items are appended to the list
+bool
+AlbumItemCb(media_album_h album, void* pUserdata)
+{
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+ media_album_h new_album = NULL;
+ ret = media_album_clone(&new_album, album);
+ SysTryLog(NID_CNT, ret == MEDIA_CONTENT_ERROR_NONE, "[E_SYSTEM] Failed to perform media_album_clone");
+
+ GList** pList = (GList**)pUserdata;
+ *pList = g_list_append(*pList, new_album);
+
+ return true;
+}
+
+}}