Merge lp:~mhr3/unity-lens-files/with-locate into lp:unity-lens-files
- with-locate
- Merge into trunk
Status: | Merged |
---|---|
Approved by: | Didier Roche-Tolomelli |
Approved revision: | 218 |
Merged at revision: | 213 |
Proposed branch: | lp:~mhr3/unity-lens-files/with-locate |
Merge into: | lp:unity-lens-files |
Diff against target: |
459 lines (+247/-25) 9 files modified
.bzrignore (+4/-0) configure.ac (+7/-0) data/Makefile.am (+13/-1) data/com.canonical.Unity.FilesLens.gschema.xml.in.in (+9/-0) src/Makefile.am (+1/-0) src/daemon.vala (+100/-11) src/locate.vala (+82/-0) src/utils.vala (+20/-13) tests/manual/locate.txt (+11/-0) |
To merge this branch: | bzr merge lp:~mhr3/unity-lens-files/with-locate |
Related bugs: |
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
Didier Roche-Tolomelli | Approve | ||
Review via email: mp+95521@code.launchpad.net |
Commit message
Description of the change
Use locate to make sure we're able to find files which aren't logged by Zeitgeist. Also adds a gsettings schema where this can be easily disabled.
UNBLOCK
Mikkel Kamstrup Erlandsen (kamstrup) wrote : | # |
- 214. By Michal Hruby
-
Simplify cancellable usage
- 215. By Michal Hruby
-
Remove an unrelated fix, deserves its own branch
Michal Hruby (mhr3) wrote : | # |
> 175 + /* We want to display something once dash is shown */
> 176 + scope.queue_
>
> I think this deserves a branch and bug report on its own.
Fair enough. Removing from this branch.
>
>
> 240 + if (cancellable.
> ("Cancelled");
>
> Can you add a more useful message, like "Cancelled locate search for '%s'" or
> something?
>
Actually I should be just using cancellable.
Moreover, daemon.vala:428:
} catch (IOError.CANCELLED ioe) {
return;
>
> 242 + var results = yield Locate.locate (query, cancellable);
> 243 + results.sort (Utils.
>
> Should we not be checking cancellable before proceeding after the async call?
>
No, an IOError is thrown in that case.
Mikkel Kamstrup Erlandsen (kamstrup) wrote : | # |
> > 242 + var results = yield Locate.locate (query, cancellable);
> > 243 + results.sort (Utils.
> >
> > Should we not be checking cancellable before proceeding after the async
> call?
> >
>
> No, an IOError is thrown in that case.
Not necessarily. If I understand GIO correctly it will raise G_IO_ERROR_
Mikkel Kamstrup Erlandsen (kamstrup) wrote : | # |
I tested it out on my netbook and it was pretty smooth.
During testing I still couldn't help getting a creepy feeling that I was seeing an alarmingly low signal to noise ratio in the results. This is not a problem for people who can immediately recognize that they are seeing a bunch of system files, but for mortal users this must be most disconcerting.
I have a feeling that we should blacklist /usr /bin /lib /opt and /var.
The results of this tool on a multi user system is also pretty angst provoking...
Michal Hruby (mhr3) wrote : | # |
> Not necessarily. If I understand GIO correctly it will raise G_IO_ERROR_
Sorted out on IRC.
> I tested it out on my netbook and it was pretty smooth.
>
> During testing I still couldn't help getting a creepy feeling that I was
> seeing an alarmingly low signal to noise ratio in the results. This is not a
> problem for people who can immediately recognize that they are seeing a bunch
> of system files, but for mortal users this must be most disconcerting.
> so because we have no contextual information on all of these system files.
>
> I have a feeling that we should blacklist /usr /bin /lib /opt and /var.
>
> The results of this tool on a multi user system is also pretty angst
> provoking...
Oh I remember we talked about filtering out of non-writable files, this branch isn't doing that yet, does anyone see any problems with adding it? (unfortunately it'll have to be post-locate filtering)
Mikkel Kamstrup Erlandsen (kamstrup) wrote : | # |
> > I have a feeling that we should blacklist /usr /bin /lib /opt and /var.
> >
> > The results of this tool on a multi user system is also pretty angst
> > provoking...
>
> Oh I remember we talked about filtering out of non-writable files, this branch
> isn't doing that yet, does anyone see any problems with adding it?
> (unfortunately it'll have to be post-locate filtering)
You're right forgot about that trick. I like that a lot better.
Sebastien Bacher (seb128) wrote : | # |
couldn't you just limit the results to the user and /media,mnt? That would solve the "too much noise" and "other user files are listed"...
Sebastien Bacher (seb128) wrote : | # |
to the user "directory"...
- 216. By Michal Hruby
-
Filter out backup files and files that are not writable
Michal Hruby (mhr3) wrote : | # |
Pushed a version which filters out non-writable files, limiting the search to a couple of directories required using --regex for locate and that slowed it down far too much (up to 8 seconds for some queries on my system)
Mikkel Kamstrup Erlandsen (kamstrup) wrote : | # |
On 2 March 2012 17:12, Michal Hruby <email address hidden> wrote:
> Pushed a version which filters out non-writable files, limiting the search to a couple of directories required using --regex for locate and that slowed it down far too much (up to 8 seconds for some queries on my system)
I am seeing some confusing matching... Searching for 'config' gives me
6 hits while searching for 'config.' gives me 81 hits... Do you know
what gives?
Also, this kind of spurious matching behaviour will inevitably pop out
here and there, but that is a price we'll have to agree to pay...
- 217. By Michal Hruby
-
Add manual test for locate scope
- 218. By Michal Hruby
-
Make sure the manual-test performer uses touch (and didrocks will live happily ever after)
Didier Roche-Tolomelli (didrocks) wrote : | # |
Ok, Michal ensured me that the technical concerns from Mikkel have been addressed. Now that there is a manual test for it (maybe some autopilot one day if we can run some command as root?) that's good for me (and it had a few days of testing already in the ubuntu-desktop ppa).
Nice to see a fix for that, well done :)
Preview Diff
1 | === modified file '.bzrignore' |
2 | --- .bzrignore 2011-08-07 09:01:34 +0000 |
3 | +++ .bzrignore 2012-03-08 16:33:30 +0000 |
4 | @@ -1,6 +1,7 @@ |
5 | src/config.c |
6 | src/daemon.c |
7 | src/folder.c |
8 | +src/locate.c |
9 | src/main.c |
10 | src/schemas.c |
11 | src/url-checker.c |
12 | @@ -43,6 +44,9 @@ |
13 | data/Makefile |
14 | data/Makefile.in |
15 | data/unity-lens-files.service |
16 | +data/com.canonical.Unity.FilesLens.gschema.valid |
17 | +data/com.canonical.Unity.FilesLens.gschema.xml |
18 | +data/com.canonical.Unity.FilesLens.gschema.xml.in |
19 | src/Makefile |
20 | src/Makefile.in |
21 | src/config.vala |
22 | |
23 | === modified file 'configure.ac' |
24 | --- configure.ac 2012-02-17 10:43:57 +0000 |
25 | +++ configure.ac 2012-03-08 16:33:30 +0000 |
26 | @@ -100,6 +100,12 @@ |
27 | fi |
28 | AC_SUBST(DBUSSERVICEDIR) |
29 | |
30 | +############################################# |
31 | +# GSettings macros |
32 | +############################################# |
33 | + |
34 | +GLIB_GSETTINGS |
35 | + |
36 | ##################################################### |
37 | # Look for correct Lenses dir |
38 | ##################################################### |
39 | @@ -117,6 +123,7 @@ |
40 | Makefile |
41 | files.lens.in |
42 | data/Makefile |
43 | + data/com.canonical.Unity.FilesLens.gschema.xml.in |
44 | src/Makefile |
45 | src/config.vala |
46 | po/Makefile.in |
47 | |
48 | === modified file 'data/Makefile.am' |
49 | --- data/Makefile.am 2011-08-04 14:15:30 +0000 |
50 | +++ data/Makefile.am 2012-03-08 16:33:30 +0000 |
51 | @@ -5,8 +5,20 @@ |
52 | %.service: %.service.in |
53 | sed -e "s|\@libexecdir\@|$(libexecdir)|" $< > $@ |
54 | |
55 | +############################################################# |
56 | +# GSettings schemas |
57 | +############################################################# |
58 | +gsettings_SCHEMAS = com.canonical.Unity.FilesLens.gschema.xml |
59 | + |
60 | +@INTLTOOL_XML_NOMERGE_RULE@ |
61 | + |
62 | +@GSETTINGS_RULES@ |
63 | + |
64 | EXTRA_DIST = \ |
65 | + com.canonical.Unity.FilesLens.gschema.xml.in.in \ |
66 | $(service_in_files) |
67 | |
68 | CLEANFILES = \ |
69 | - unity-lens-files.service |
70 | + unity-lens-files.service \ |
71 | + $(gsettings_SCHEMAS) |
72 | + |
73 | |
74 | === added file 'data/com.canonical.Unity.FilesLens.gschema.xml.in.in' |
75 | --- data/com.canonical.Unity.FilesLens.gschema.xml.in.in 1970-01-01 00:00:00 +0000 |
76 | +++ data/com.canonical.Unity.FilesLens.gschema.xml.in.in 2012-03-08 16:33:30 +0000 |
77 | @@ -0,0 +1,9 @@ |
78 | +<schemalist> |
79 | + <schema path="/desktop/unity/lenses/files/" id="com.canonical.Unity.FilesLens" gettext-domain="unity-lens-files"> |
80 | + <key type="b" name="use-locate"> |
81 | + <default>true</default> |
82 | + <summary>Use locate during searches.</summary> |
83 | + <description>Use locate during searches to make sure the lens is able to find most of their files even it they're not logged by Zeitgeist.</description> |
84 | + </key> |
85 | + </schema> |
86 | +</schemalist> |
87 | |
88 | === modified file 'src/Makefile.am' |
89 | --- src/Makefile.am 2011-09-29 10:19:09 +0000 |
90 | +++ src/Makefile.am 2012-03-08 16:33:30 +0000 |
91 | @@ -39,6 +39,7 @@ |
92 | config.vala \ |
93 | daemon.vala \ |
94 | folder.vala \ |
95 | + locate.vala \ |
96 | main.vala \ |
97 | schemas.vala \ |
98 | url-checker.vala \ |
99 | |
100 | === modified file 'src/daemon.vala' |
101 | --- src/daemon.vala 2012-02-14 13:44:37 +0000 |
102 | +++ src/daemon.vala 2012-03-08 16:33:30 +0000 |
103 | @@ -1,5 +1,5 @@ |
104 | /* |
105 | - * Copyright (C) 2010 Canonical Ltd |
106 | + * Copyright (C) 2010-2012 Canonical Ltd |
107 | * |
108 | * This program is free software: you can redistribute it and/or modify |
109 | * it under the terms of the GNU General Public License version 3 as |
110 | @@ -14,6 +14,7 @@ |
111 | * along with this program. If not, see <http://www.gnu.org/licenses/>. |
112 | * |
113 | * Authored by Mikkel Kamstrup Erlandsen <mikkel.kamstrup@canonical.com> |
114 | + * Michal Hruby <michal.hruby@canonical.com> |
115 | * |
116 | */ |
117 | using Zeitgeist; |
118 | @@ -41,9 +42,22 @@ |
119 | * we use to query Zeitgeist */ |
120 | private HashTable<string, Event> type_templates; |
121 | |
122 | + private const string SCHEMA_NAME = "com.canonical.Unity.FilesLens"; |
123 | + private const string USE_LOCATE_KEY = "use-locate"; |
124 | + public bool use_locate { get; set; default = true; } |
125 | + |
126 | + private Settings lens_settings; |
127 | + |
128 | construct |
129 | { |
130 | - prepare_type_templates(); |
131 | + prepare_type_templates (); |
132 | + |
133 | + if (SCHEMA_NAME in Settings.list_schemas ()) |
134 | + { |
135 | + lens_settings = new Settings (SCHEMA_NAME); |
136 | + lens_settings.bind (USE_LOCATE_KEY, this, USE_LOCATE_KEY, |
137 | + SettingsBindFlags.GET); |
138 | + } |
139 | |
140 | scope = new Unity.Scope ("/com/canonical/unity/scope/files"); |
141 | scope.search_in_global = true; |
142 | @@ -54,15 +68,15 @@ |
143 | lens.search_hint = _("Search Files & Folders"); |
144 | lens.visible = true; |
145 | populate_categories (); |
146 | - populate_filters(); |
147 | + populate_filters (); |
148 | lens.add_local_scope (scope); |
149 | |
150 | /* Bring up Zeitgeist interfaces */ |
151 | - log = new Zeitgeist.Log(); |
152 | - index = new Zeitgeist.Index(); |
153 | + log = new Zeitgeist.Log (); |
154 | + index = new Zeitgeist.Index (); |
155 | |
156 | /* Listen for all file:// related events from Zeitgeist */ |
157 | - var templates = new PtrArray(); |
158 | + var templates = new PtrArray (); |
159 | var event = new Zeitgeist.Event (); |
160 | var subject = new Zeitgeist.Subject (); |
161 | subject.set_uri ("file://*"); |
162 | @@ -73,7 +87,7 @@ |
163 | monitor.events_inserted.connect (on_zeitgeist_changed); |
164 | monitor.events_deleted.connect (on_zeitgeist_changed); |
165 | log.install_monitor (monitor); |
166 | - |
167 | + |
168 | bookmarks = new Bookmarks (); |
169 | urls = new UrlChecker (); |
170 | |
171 | @@ -400,6 +414,14 @@ |
172 | search.search_string); |
173 | } |
174 | |
175 | + if (has_search && use_locate) |
176 | + { |
177 | + yield perform_locate (500, search.search_string, |
178 | + search.results_model, cancellable, |
179 | + Categories.FILES_AND_FOLDERS, |
180 | + Categories.FILES_AND_FOLDERS); |
181 | + } |
182 | + |
183 | } catch (IOError.CANCELLED ioe) { |
184 | return; |
185 | } catch (GLib.Error e) { |
186 | @@ -504,6 +526,12 @@ |
187 | if (!txn.is_committed ()) txn.commit (); |
188 | } |
189 | |
190 | + if (has_search && use_locate) |
191 | + { |
192 | + yield perform_locate (500, search.search_string, |
193 | + search.results_model, cancellable); |
194 | + } |
195 | + |
196 | } catch (IOError.CANCELLED ioe) { |
197 | return; |
198 | } catch (GLib.Error e) { |
199 | @@ -710,9 +738,8 @@ |
200 | return; |
201 | } |
202 | |
203 | - if (cancellable.is_cancelled ()) |
204 | - throw new IOError.CANCELLED ("Search was cancelled"); |
205 | - |
206 | + cancellable.set_error_if_cancelled (); // throws IOError |
207 | + |
208 | /* Sort files by mtime, we do an ugly nested ternary |
209 | * to avoid potential long/int overflow */ |
210 | downloads.sort ((CompareFunc) Utils.cmp_file_info_by_mtime); |
211 | @@ -720,6 +747,7 @@ |
212 | var timerange = get_current_timerange (); |
213 | int64 min_size, max_size; |
214 | get_current_size_limits (out min_size, out max_size); |
215 | + var types = get_current_types (); |
216 | |
217 | foreach (var info in downloads) |
218 | { |
219 | @@ -734,7 +762,6 @@ |
220 | continue; |
221 | |
222 | // check if type matches |
223 | - var types = get_current_types (); |
224 | if (types != null && !Utils.file_info_matches_any (info, types)) |
225 | continue; |
226 | |
227 | @@ -753,6 +780,68 @@ |
228 | } |
229 | } |
230 | |
231 | + private async void perform_locate (uint timeout, |
232 | + string query, |
233 | + Dee.Model results_model, |
234 | + Cancellable cancellable, |
235 | + int files_category = Categories.RECENT, |
236 | + int dirs_category = Categories.FOLDERS) |
237 | + throws Error |
238 | + { |
239 | + /* Wait a while before starting the locate search */ |
240 | + Timeout.add_full (Priority.LOW, timeout, perform_locate.callback); |
241 | + yield; |
242 | + cancellable.set_error_if_cancelled (); // throws IOError |
243 | + |
244 | + var results = yield Locate.locate (query, cancellable); |
245 | + results.sort (Utils.cmp_file_info_by_mtime); |
246 | + |
247 | + /* make a list of uris we already have */ |
248 | + var present_uris = new Gee.HashSet<string> (); |
249 | + var model_iter = results_model.get_first_iter (); |
250 | + var model_end_iter = results_model.get_last_iter (); |
251 | + while (model_iter != model_end_iter) |
252 | + { |
253 | + present_uris.add (results_model.get_string (model_iter, 0)); |
254 | + model_iter = results_model.next (model_iter); |
255 | + } |
256 | + |
257 | + var timerange = get_current_timerange (); |
258 | + int64 min_size, max_size; |
259 | + get_current_size_limits (out min_size, out max_size); |
260 | + var types = get_current_types (); |
261 | + |
262 | + foreach (var info in results) |
263 | + { |
264 | + var uri = info.get_data<File> ("associated-gfile").get_uri (); |
265 | + warn_if_fail (uri != null); |
266 | + if (uri == null || uri in present_uris) continue; |
267 | + var mimetype = info.get_attribute_string (FILE_ATTRIBUTE_STANDARD_FAST_CONTENT_TYPE); |
268 | + var icon_hint = Utils.check_icon_string (uri, mimetype, info); |
269 | + |
270 | + // check if we match the timerange |
271 | + uint64 mtime = info.get_attribute_uint64 (FILE_ATTRIBUTE_TIME_MODIFIED) * 1000; |
272 | + |
273 | + if (mtime < timerange.get_start() || mtime > timerange.get_end ()) |
274 | + continue; |
275 | + |
276 | + // check if type matches |
277 | + if (types != null && !Utils.file_info_matches_any (info, types)) |
278 | + continue; |
279 | + |
280 | + // check if size is within bounds |
281 | + int64 size = info.get_size (); |
282 | + if (size < min_size || size > max_size) |
283 | + continue; |
284 | + |
285 | + uint category_id = mimetype == "inode/directory" ? |
286 | + dirs_category : files_category; |
287 | + |
288 | + results_model.append (uri, icon_hint, category_id, |
289 | + mimetype, info.get_display_name (), uri); |
290 | + } |
291 | + } |
292 | + |
293 | public Unity.ActivationResponse activate (string uri) |
294 | { |
295 | debug (@"Activating: $uri"); |
296 | |
297 | === added file 'src/locate.vala' |
298 | --- src/locate.vala 1970-01-01 00:00:00 +0000 |
299 | +++ src/locate.vala 2012-03-08 16:33:30 +0000 |
300 | @@ -0,0 +1,82 @@ |
301 | +/* |
302 | + * Copyright (C) 2010-2012 Canonical Ltd |
303 | + * |
304 | + * This program is free software: you can redistribute it and/or modify |
305 | + * it under the terms of the GNU General Public License version 3 as |
306 | + * published by the Free Software Foundation. |
307 | + * |
308 | + * This program is distributed in the hope that it will be useful, |
309 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
310 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
311 | + * GNU General Public License for more details. |
312 | + * |
313 | + * You should have received a copy of the GNU General Public License |
314 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
315 | + * |
316 | + * Authored by Michal Hruby <michal.hruby@canonical.com> |
317 | + * |
318 | + */ |
319 | +using Zeitgeist; |
320 | +using Config; |
321 | +using Gee; |
322 | + |
323 | +namespace Unity.FilesLens.Locate |
324 | +{ |
325 | + const uint MAX_RESULTS = 128; |
326 | + |
327 | + /* Careful about usage of FILE_ATTRIBUTE_STANDARD_ICON, this is the same as |
328 | + * requesting FILE_ATTRIBUTE_STANDARD_CONTENT_TYPE and causes reading |
329 | + * of the target file, we just want to stat it */ |
330 | + const string ATTRIBS = FILE_ATTRIBUTE_STANDARD_IS_HIDDEN + "," + |
331 | + FILE_ATTRIBUTE_STANDARD_IS_BACKUP + "," + |
332 | + FILE_ATTRIBUTE_STANDARD_DISPLAY_NAME + "," + |
333 | + FILE_ATTRIBUTE_STANDARD_SIZE + "," + |
334 | + FILE_ATTRIBUTE_TIME_MODIFIED + "," + |
335 | + FILE_ATTRIBUTE_THUMBNAIL_PATH + "," + |
336 | + FILE_ATTRIBUTE_ACCESS_CAN_WRITE + "," + |
337 | + FILE_ATTRIBUTE_STANDARD_FAST_CONTENT_TYPE; |
338 | + |
339 | + public async GLib.SList<FileInfo> locate (string input_query, |
340 | + Cancellable cancellable) throws Error |
341 | + { |
342 | + var result = new GLib.SList<FileInfo> (); |
343 | + var query = Regex.escape_string (input_query.strip ()); |
344 | + |
345 | + // FIXME: we could limit the search to specific directories, but using regex |
346 | + // matching slows down the search considerably |
347 | + string[] argv = { "locate", "-i", "-e", "-l", "%u".printf (MAX_RESULTS), |
348 | + "*%s*".printf (query.replace (" ", "*")) }; |
349 | + |
350 | + Pid pid; |
351 | + int read_fd; |
352 | + string? line = null; |
353 | + |
354 | + Process.spawn_async_with_pipes (null, argv, null, SpawnFlags.SEARCH_PATH, |
355 | + null, out pid, null, out read_fd); |
356 | + |
357 | + UnixInputStream read_stream = new UnixInputStream (read_fd, true); |
358 | + DataInputStream locate_output = new DataInputStream (read_stream); |
359 | + |
360 | + do |
361 | + { |
362 | + line = yield locate_output.read_line_async (Priority.DEFAULT_IDLE, |
363 | + cancellable); |
364 | + if (line == null) break; |
365 | + if ("/." in line) continue; // we don't want no hidden files |
366 | + |
367 | + var file = File.new_for_path (line); |
368 | + var fi = yield file.query_info_async (ATTRIBS, 0, Priority.DEFAULT_IDLE, |
369 | + cancellable); |
370 | + if (fi.get_is_hidden () || fi.get_is_backup () || |
371 | + !fi.get_attribute_boolean (FILE_ATTRIBUTE_ACCESS_CAN_WRITE)) continue; |
372 | + fi.set_data ("associated-gfile", file); |
373 | + result.prepend (fi); |
374 | + |
375 | + } while (line != null); |
376 | + |
377 | + result.reverse (); |
378 | + return result; |
379 | + } |
380 | + |
381 | +} /* namespace */ |
382 | + |
383 | |
384 | === modified file 'src/utils.vala' |
385 | --- src/utils.vala 2012-01-27 17:14:56 +0000 |
386 | +++ src/utils.vala 2012-03-08 16:33:30 +0000 |
387 | @@ -85,23 +85,25 @@ |
388 | |
389 | public string check_icon_string (string uri, string mimetype, FileInfo info) |
390 | { |
391 | - Icon icon = info.get_icon(); |
392 | + Icon icon = info.get_icon (); |
393 | string thumbnail_path = info.get_attribute_byte_string (FILE_ATTRIBUTE_THUMBNAIL_PATH); |
394 | |
395 | - if (thumbnail_path == null) |
396 | - return icon.to_string(); |
397 | + if (thumbnail_path == null && icon != null) |
398 | + return icon.to_string (); |
399 | + else if (icon == null) |
400 | + return ContentType.get_icon (mimetype).to_string (); |
401 | else |
402 | - return new FileIcon(File.new_for_path (thumbnail_path)).to_string (); |
403 | + return new FileIcon (File.new_for_path (thumbnail_path)).to_string (); |
404 | } |
405 | |
406 | - public int cmp_file_info_by_mtime (FileInfo info1, FileInfo info2) |
407 | - { |
408 | - TimeVal tv1, tv2; |
409 | - info1.get_modification_time (out tv1); |
410 | - info2.get_modification_time (out tv2); |
411 | - long cmp = tv1.tv_sec - tv2.tv_sec; |
412 | - return cmp < 0 ? 1 : ( cmp > 0 ? -1 : 0); |
413 | - } |
414 | + public int cmp_file_info_by_mtime (FileInfo info1, FileInfo info2) |
415 | + { |
416 | + TimeVal tv1, tv2; |
417 | + info1.get_modification_time (out tv1); |
418 | + info2.get_modification_time (out tv2); |
419 | + long cmp = tv1.tv_sec - tv2.tv_sec; |
420 | + return cmp < 0 ? 1 : ( cmp > 0 ? -1 : 0); |
421 | + } |
422 | |
423 | public string get_month_name (DateMonth month) |
424 | { |
425 | @@ -333,10 +335,15 @@ |
426 | |
427 | public bool file_info_matches_type (FileInfo info, string type_id) |
428 | { |
429 | + unowned string interpretation; |
430 | unowned string content_type = info.get_content_type (); |
431 | - unowned string interpretation; |
432 | + if (content_type == null) |
433 | + content_type = info.get_attribute_string (FILE_ATTRIBUTE_STANDARD_FAST_CONTENT_TYPE); |
434 | + |
435 | + if (content_type == null) content_type = "application/octet-stream"; |
436 | |
437 | interpretation = Zeitgeist.interpretation_for_mimetype (content_type); |
438 | + if (interpretation == null) return type_id == "other" || type_id == "all"; |
439 | |
440 | /* type_id is one of: documents, folders, images, audio, videos, |
441 | * presentations, other */ |
442 | |
443 | === added directory 'tests' |
444 | === added directory 'tests/manual' |
445 | === added file 'tests/manual/locate.txt' |
446 | --- tests/manual/locate.txt 1970-01-01 00:00:00 +0000 |
447 | +++ tests/manual/locate.txt 2012-03-08 16:33:30 +0000 |
448 | @@ -0,0 +1,11 @@ |
449 | +Locate scope |
450 | +============ |
451 | +Tests that the locate scope works. |
452 | + |
453 | +#. Create a file named "report.txt" in your home directory (`touch report.txt`). |
454 | +#. Run updatedb (`sudo updatedb`). |
455 | +#. Search for this file with files lens. |
456 | + |
457 | +Outcome |
458 | + The "report.txt" should show up as a result in the Recent category of files lens. |
459 | + |
175 + /* We want to display something once dash is shown */ search_ changed (SearchType. GLOBAL) ;
176 + scope.queue_
I think this deserves a branch and bug report on its own.
240 + if (cancellable. is_cancelled ()) throw new IOError.CANCELLED ("Cancelled");
Can you add a more useful message, like "Cancelled locate search for '%s'" or something?
242 + var results = yield Locate.locate (query, cancellable); cmp_file_ info_by_ mtime);
243 + results.sort (Utils.
Should we not be checking cancellable before proceeding after the async call?
Otherwise, awesome work! It works quite well here on my sandybridge lappy. I wanna test this on my elcheapo netbook before I give it the final ack.