Release 4.0.0-preview1-00172
[platform/core/csapi/tizenfx.git] / src / Tizen.Content.MediaContent / Tizen.Content.MediaContent / QueryArguments.cs
1 /*
2  * Copyright (c) 2016 Samsung Electronics Co., Ltd All Rights Reserved
3  *
4  * Licensed under the Apache License, Version 2.0 (the License);
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an AS IS BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17 using System;
18 using System.Diagnostics;
19 using FilterHandle = Interop.FilterHandle;
20
21 namespace Tizen.Content.MediaContent
22 {
23     /// <summary>
24     /// The Base class for query arguments.
25     /// </summary>
26     /// <remarks>
27     /// A filter is required for filtering information associated with Album, Folder, Tag, Bookmark, Playlist,
28     /// and MediaInfo on the basis of details like limit, order, and condition.
29     /// </remarks>
30     public class QueryArguments
31     {
32         private string _filter;
33
34         /// <summary>
35         /// Gets or sets the filtering expression that is applied.
36         /// </summary>
37         /// <value>A string that represents a filtering expression applied when data is retrieved.</value>
38         /// <remarks>
39         /// Expressions for the filter can be one of the following forms:
40         /// <list>
41         /// <item><description>column = value</description></item>
42         /// <item><description>column > value</description></item>
43         /// <item><description>column >= value</description></item>
44         /// <item><description>column < value</description></item>
45         /// <item><description>column <= value</description></item>
46         /// <item><description>value = column</description></item>
47         /// <item><description>value >= column</description></item>
48         /// <item><description>value < column</description></item>
49         /// <item><description>value <= column</description></item>
50         /// <item><description>column IN (value)</description></item>
51         /// <item><description>column IN(value-list)</description></item>
52         /// <item><description>column NOT IN(value)</description></item>
53         /// <item><description>column NOT IN(value-list)</description></item>
54         /// <item><description>column LIKE value</description></item>
55         /// <item><description>expression COLLATE NOCASE</description></item>
56         /// <item><description>expression COLLATE RTRIM</description></item>
57         /// <item><description>expression COLLATE LOCALIZED</description></item>
58         /// <item><description>expression1 AND expression2 OR expression3 ... </description></item>
59         /// </list>
60         ///
61         /// Note that if you want to set quotation (" ' " or " " ") as value of LIKE operator, you should use two times. (" '' " or " "" ").
62         /// And the optional ESCAPE clause is supported. Both percent symbol("%") and underscore symbol("_") are used in the LIKE pattern.
63         /// If these characters are used as values of the LIKE operation, then the expression following the ESCAPE clause of sqlite will be ignored.\n
64         /// \n
65         /// For example,\n
66         /// - column LIKE ('#%') ESCAPE ('#') - "#" is an escape character, it will be ignored.
67         /// </remarks>
68         /// <exception cref="ArgumentException"><paramref name="value"/> is a zero-length string, contains only white space.</exception>
69         /// <seealso cref="MediaInfoColumns"/>
70         /// <seealso cref="AlbumColumns"/>
71         /// <seealso cref="FolderColumns"/>
72         /// <seealso cref="PlaylistColumns"/>
73         /// <seealso cref="TagColumns"/>
74         /// <seealso cref="BookmarkColumns"/>
75         /// <seealso cref="FaceInfoColumns"/>
76         public string FilterExpression
77         {
78             get => _filter;
79             set
80             {
81                 if (value != null)
82                 {
83                     ValidationUtil.ValidateNotNullOrEmpty(value, nameof(value));
84                 }
85
86                 _filter = value;
87             }
88         }
89
90         private string _storageId;
91
92         /// <summary>
93         /// Gets or sets the storage ID for the given filter.
94         /// You can use this property when you want to search items only in the specific storage.
95         /// </summary>
96         /// <value>The storage ID to restrict storage to search, or null for all storages.</value>
97         /// <exception cref="ArgumentException"><paramref name="value"/> is a zero-length string, contains only white space.</exception>
98         public string StorageId
99         {
100             get => _storageId;
101             set
102             {
103                 if (value != null)
104                 {
105                     ValidationUtil.ValidateNotNullOrEmpty(value, nameof(value));
106                 }
107
108                 _storageId = value;
109             }
110         }
111
112         internal static FilterHandle ToNativeHandle(QueryArguments arguments)
113         {
114             if (arguments == null || arguments.IsEmpty())
115             {
116                 return FilterHandle.Null;
117             }
118
119             Interop.Filter.Create(out var handle).ThrowIfError("Failed to apply arguments.");
120
121             try
122             {
123                 arguments.FillHandle(handle);
124             }
125             catch (Exception)
126             {
127                 handle.Dispose();
128                 throw;
129             }
130
131             return handle;
132         }
133
134         internal static FilterHandle CreateNativeHandle(string filterExpression)
135         {
136             Debug.Assert(filterExpression != null);
137
138             Interop.Filter.Create(out var handle).ThrowIfError("Failed to apply arguments.");
139
140             Interop.Filter.SetCondition(handle, filterExpression, Collation.Default).
141                 ThrowIfError("Failed to create filter handle.");
142
143             return handle;
144         }
145
146         internal virtual bool IsEmpty()
147         {
148             return StorageId == null && FilterExpression == null;
149         }
150
151         internal virtual void FillHandle(FilterHandle handle)
152         {
153             if (FilterExpression != null)
154             {
155                 Interop.Filter.SetCondition(handle, FilterExpression, Collation.Default).
156                     ThrowIfError("Failed to create filter handle(condition)");
157             }
158
159             if (StorageId != null)
160             {
161                 Interop.Filter.SetStorage(handle, StorageId).
162                     ThrowIfError("Failed to create filter handle(storage id)"); ;
163             }
164         }
165     }
166
167     /// <summary>
168     /// Provides the ability to filter the result of a Select command.
169     /// </summary>
170     /// <remarks>
171     /// A filter is required for filtering information associated with Album, Folder, Tag, Bookmark, Playlist,
172     /// and MediaInfo.
173     /// </remarks>
174     public class SelectArguments : QueryArguments
175     {
176         private int _startRowIndex;
177
178         /// <summary>
179         /// Gets or sets the starting row position of a query (starting from zero).
180         /// </summary>
181         /// <value>An integer value that indicates the starting row position of a query.</value>
182         /// <exception cref="ArgumentOutOfRangeException"><paramref name="value"/> is less than zero.\n</exception>
183         public int StartRowIndex
184         {
185             get => _startRowIndex;
186             set
187             {
188                 if (value < 0)
189                 {
190                     throw new ArgumentOutOfRangeException(nameof(value), value, "StartRowIndex can't be less than zero.");
191                 }
192
193                 _startRowIndex = value;
194             }
195         }
196
197         private int _totalRowCount;
198
199         /// <summary>
200         /// Gets or sets the number of rows to be retrieved.
201         /// </summary>
202         /// <value>An integer value that indicates the limit of rows of the result.</value>
203         /// <exception cref="ArgumentOutOfRangeException"><paramref name="value"/> is less than zero.</exception>
204         public int TotalRowCount
205         {
206             get => _totalRowCount;
207             set
208             {
209                 if (value < 0)
210                 {
211                     throw new ArgumentOutOfRangeException(nameof(value), value, "TotalRowCount can't be less than zero.");
212                 }
213
214                 _totalRowCount = value;
215             }
216         }
217
218         private string _sortOrder;
219
220         /// <summary>
221         /// Gets or sets the sort order of the results.
222         /// </summary>
223         /// <value>The expression for the sort order.</value>
224         /// <remarks>
225         /// Expressions for the sort order can be:\n
226         /// column [COLLATE NOCASE/RTRIM/LOCALIZED] [ASC/DESC], column2 ...
227         /// </remarks>
228         /// <exception cref="ArgumentException"><paramref name="value"/> is a zero-length string, contains only white space.</exception>
229         /// <seealso cref="MediaInfoColumns"/>
230         /// <seealso cref="AlbumColumns"/>
231         /// <seealso cref="FolderColumns"/>
232         /// <seealso cref="PlaylistColumns"/>
233         /// <seealso cref="TagColumns"/>
234         /// <seealso cref="BookmarkColumns"/>
235         /// <seealso cref="FaceInfoColumns"/>
236         public string SortOrder
237         {
238             get => _sortOrder;
239             set
240             {
241                 if (value != null)
242                 {
243                     ValidationUtil.ValidateNotNullOrEmpty(value, nameof(value));
244                 }
245
246                 _sortOrder = value;
247             }
248         }
249
250         internal override bool IsEmpty()
251         {
252             return base.IsEmpty() && StartRowIndex == 0 && TotalRowCount == 0 && SortOrder == null;
253         }
254
255         internal override void FillHandle(FilterHandle handle)
256         {
257             base.FillHandle(handle);
258
259             if (StartRowIndex != 0 || TotalRowCount != 0)
260             {
261                 Interop.Filter.SetOffset(handle, StartRowIndex, TotalRowCount).
262                     ThrowIfError("Failed to create filter handle(limit)");
263             }
264
265             if (SortOrder != null)
266             {
267                 Interop.Filter.SetOrder(handle, SortOrder).ThrowIfError("Failed to create filter handle(order)");
268             }
269         }
270     }
271
272     /// <summary>
273     /// Provides the ability to filter the result of the Count command.
274     /// </summary>
275     /// <remarks>
276     /// A filter is required for filtering information associated with Album, Folder, Tag, Bookmark, Playlist,
277     /// and MediaInfo.
278     /// </remarks>
279     public class CountArguments : QueryArguments
280     {
281     }
282 }