~ubuntu-branches/ubuntu/jaunty/beagle/jaunty-security

« back to all changes in this revision

Viewing changes to tools/StaticQuery.cs

  • Committer: Bazaar Package Importer
  • Author(s): Stefan Ebner
  • Date: 2008-05-04 00:31:32 UTC
  • mfrom: (1.1.21 upstream)
  • Revision ID: james.westby@ubuntu.com-20080504003132-2tkm5o8moo5952ri
Tags: 0.3.7-2ubuntu1
 * Merge from Debian unstable. (LP: #225746) Remaining Ubuntu changes:
  - debian/control:
    + Rename ice{weasel,dove}-beagle to {mozilla,thunderbird}-beagle and
      and update the dependencies accordingly.
    + Change Maintainer to Ubuntu Mono Team.
  - debian/rules:
    + Install the mozilla-beagle and thunderbird-beagle extensions.
  - ice{dove,weasel}.dirs:
    + Renamed to {mozilla,thunderbird}-beagle.dirs.
    + Fixed paths to point to usr/lib/{firefox,thunderbird}

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
//
 
2
// StaticQuery.cs
 
3
//
 
4
// Copyright (C) 2008 D Bera <dbera.web@gmail.com>
 
5
// Copyright (C) 2004-2006 Novell, Inc.
 
6
//
 
7
 
 
8
//
 
9
// Permission is hereby granted, free of charge, to any person obtaining a copy
 
10
// of this software and associated documentation files (the "Software"), to deal
 
11
// in the Software without restriction, including without limitation the rights
 
12
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 
13
// copies of the Software, and to permit persons to whom the Software is
 
14
// furnished to do so, subject to the following conditions:
 
15
//
 
16
// The above copyright notice and this permission notice shall be included in all
 
17
// copies or substantial portions of the Software.
 
18
//
 
19
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 
20
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 
21
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 
22
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 
23
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 
24
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
 
25
// SOFTWARE.
 
26
//
 
27
 
 
28
using System;
 
29
using System.IO;
 
30
using System.Collections;
 
31
using System.Collections.Generic;
 
32
using System.Reflection;
 
33
using System.Text;
 
34
using System.Runtime.InteropServices;
 
35
 
 
36
using GLib;
 
37
 
 
38
using Beagle;
 
39
using Beagle.Util;
 
40
using Beagle.Daemon;
 
41
 
 
42
// Assembly information
 
43
[assembly: AssemblyTitle ("beagle-static-query")]
 
44
[assembly: AssemblyDescription ("Command-line interface to query the Beagle index")]
 
45
 
 
46
public class QueryTool {
 
47
 
 
48
        private static int count = 0;
 
49
        private static Query query = null;
 
50
        private static DateTime queryStartTime;
 
51
        private static DateTime lastQueryTime = DateTime.Now;
 
52
 
 
53
        // CLI args
 
54
        private static bool verbose = false;
 
55
        private static bool display_hits = true;
 
56
        private static bool display_cached_text = false;
 
57
 
 
58
        private static void OnHitsAdded (QueryResult result, ICollection hits, int num_hits)
 
59
        {
 
60
                lastQueryTime = DateTime.Now;
 
61
 
 
62
                if (count == 0 && verbose) {
 
63
                        Console.WriteLine ("First hit returned in {0:0.000}s",
 
64
                                           (lastQueryTime - queryStartTime).TotalSeconds);
 
65
                }
 
66
 
 
67
                if (verbose && num_hits >= 0)
 
68
                        Console.WriteLine ("Returned latest {0} results out of total {1} matches", hits.Count, num_hits);
 
69
 
 
70
                if (! display_hits) {
 
71
                        count += hits.Count;
 
72
                        return;
 
73
                }
 
74
 
 
75
                foreach (Hit hit in hits) {
 
76
                        if (verbose)
 
77
                                Console.WriteLine ("  Uri: {0}", hit.Uri);
 
78
                        else
 
79
                                Console.WriteLine (hit.Uri);
 
80
 
 
81
                        if (verbose) {
 
82
                                SnippetRequest sreq = new SnippetRequest (query, hit);
 
83
                                if (display_cached_text)
 
84
                                        sreq.FullText = true;
 
85
 
 
86
                                List<SnippetLine> snippets = GetSnippet (sreq);
 
87
                                Console.WriteLine ("PaUri: {0}", hit.ParentUri != null ? hit.ParentUri.ToString () : "(null)");
 
88
                                if (! display_cached_text) {
 
89
                                        Console.Write (" Snip: ");
 
90
                                        if (snippets.Count == 0)
 
91
                                                Console.WriteLine ("(null)");
 
92
                                        else {
 
93
                                                foreach (SnippetLine snippet_line in snippets) {
 
94
                                                        Console.Write (snippet_line);
 
95
                                                        Console.Write (" ... ");
 
96
                                                }
 
97
 
 
98
                                                Console.WriteLine ();
 
99
                                        }
 
100
                                }
 
101
 
 
102
                                Console.WriteLine (" Type: {0}", hit.Type);
 
103
                                Console.WriteLine ("MimeT: {0}", hit.MimeType == null ? "(null)" : hit.MimeType);
 
104
                                Console.WriteLine ("  Src: {0}", hit.Source);
 
105
                                Console.WriteLine ("Score: {0}", hit.Score);
 
106
                                if (hit.ValidTimestamp)
 
107
                                        Console.WriteLine (" Time: {0}", DateTimeUtil.ToString (hit.Timestamp));
 
108
                                
 
109
                                foreach (Property prop in hit.Properties)
 
110
                                        Console.WriteLine ("    {0} = '{1}'",
 
111
                                                prop.Key,
 
112
                                                (prop.Type != PropertyType.Date ? prop.Value : DateTimeUtil.ToString (StringFu.StringToDateTime (prop.Value))));
 
113
                                
 
114
 
 
115
                                if (display_cached_text) {
 
116
                                        Console.WriteLine ("-- Cache -------------------------------------");
 
117
                                        if (snippets.Count == 0)
 
118
                                                Console.WriteLine ("(empty)");
 
119
                                        else {
 
120
                                                foreach (SnippetLine snippet_line in snippets) {
 
121
                                                        if (snippet_line == null || snippet_line.Fragments == null)
 
122
                                                                Console.WriteLine ("(empty)");
 
123
                                                        else
 
124
                                                                Console.WriteLine (((Fragment)snippet_line.Fragments [0]).Text);
 
125
                                                }
 
126
                                        }
 
127
                                        Console.WriteLine ("----------------------------------------------");
 
128
                                }
 
129
                                Console.WriteLine ();
 
130
                        }
 
131
 
 
132
                        ++count;
 
133
                }
 
134
        }
 
135
 
 
136
        private static void OnFinished (QueryResult result)
 
137
        {
 
138
                if (verbose) {
 
139
                        Console.WriteLine ("Elapsed time: {0:0.000}s",
 
140
                                           (DateTime.Now - queryStartTime).TotalSeconds);
 
141
                        Console.WriteLine ("Total hits: {0}", count);
 
142
                }
 
143
        }
 
144
 
 
145
        private static List<SnippetLine> GetSnippet (SnippetRequest request)
 
146
        {
 
147
                Queryable queryable = QueryDriver.GetQueryable (request.Hit.Source);
 
148
                ISnippetReader snippet_reader;
 
149
                bool full_text = request.FullText;
 
150
                int ctx_length = request.ContextLength;
 
151
                int snp_length = request.SnippetLength;
 
152
 
 
153
                if (queryable == null) {
 
154
                        Console.WriteLine ("SnippetExecutor: No queryable object matches '{0}'", request.Hit.Source);
 
155
                        snippet_reader = new SnippetReader (null, null, false, -1, -1);
 
156
                        full_text = false;
 
157
                } else
 
158
                        snippet_reader = queryable.GetSnippet (request.QueryTerms, request.Hit, full_text, ctx_length, snp_length);
 
159
 
 
160
                List<SnippetLine> snippetlines = new List<SnippetLine> ();
 
161
                if (snippet_reader == null)
 
162
                        return snippetlines;
 
163
 
 
164
                if (! full_text) {
 
165
                        foreach (SnippetLine snippet_line in snippet_reader.GetSnippet ())
 
166
                                snippetlines.Add (snippet_line);
 
167
                } else {
 
168
                        SnippetLine snippet_line = new SnippetLine ();
 
169
                        snippet_line.Line = 1;
 
170
 
 
171
                        Fragment fragment = new Fragment ();
 
172
                        fragment.QueryTermIndex = -1;
 
173
                        StringBuilder sb = new StringBuilder ();
 
174
 
 
175
                        string line;
 
176
                        // Read data from snippet_reader and write
 
177
                        while ((line = snippet_reader.ReadLine ()) != null) {
 
178
                                sb.Append (StringFu.CleanupInvalidXmlCharacters (line));
 
179
                                sb.Append ("\n");
 
180
                        }
 
181
 
 
182
                        fragment.Text = sb.ToString ();
 
183
                        snippet_line.Fragments = new ArrayList ();
 
184
                        snippet_line.Fragments.Add (fragment);
 
185
                        snippetlines.Add (snippet_line);
 
186
                }
 
187
 
 
188
                snippet_reader.Close ();
 
189
 
 
190
                return snippetlines;
 
191
        }
 
192
 
 
193
        public static void PrintUsageAndExit () 
 
194
        {
 
195
                VersionFu.PrintHeader ();
 
196
 
 
197
                string usage =
 
198
                        "Usage: beagle-query [OPTIONS] <query string>\n\n" +
 
199
                        "Options:\n" +
 
200
                        "  --verbose\t\tPrint detailed information about each hit.\n" +
 
201
                        "  --cache\t\tShow the entire cached text instead of a snippet\n" +
 
202
                        "         \t\tshowing the matches, requires --verbose.\n" +
 
203
                        "         \t\tFor large documents this will produce extremely large output,\n" +
 
204
                        "         \t\tso use this with uri queries or queries returning only a few results\n" + 
 
205
                        "         \t\tNot recommended for live-queries or stats-only queries.\n" +
 
206
                        "  --keywords\t\tLists the keywords allowed in 'query string'.\n" +
 
207
                        "            \t\tKeyword queries can be specified as keywordname:value e.g. ext:jpg\n" +
 
208
                        "  --stats-only\t\tOnly display statistics about the query, not\n" +
 
209
                        "              \t\tthe actual results.\n" +
 
210
                        "  --max-hits\t\tLimit number of search results per backend\n" +
 
211
                        "            \t\t(default 100)\n" +
 
212
                        "\n" +
 
213
                        "\n" +
 
214
                        "  --help\t\tPrint this usage message.\n" +
 
215
                        "  --version\t\tPrint version information.\n" +
 
216
                        "\n" +
 
217
                        "Query string supports an advanced query syntax.\n" +
 
218
                        "For details of the query syntax, please see http://beagle-project.org/Searching_Data\n" +
 
219
                        "Note: Quotes (\" or \') need to be shell escaped if used.\n";
 
220
 
 
221
                Console.WriteLine (usage);
 
222
 
 
223
                System.Environment.Exit (0);
 
224
        }
 
225
 
 
226
        [DllImport("libgobject-2.0.so.0")]
 
227
        static extern void g_type_init ();
 
228
 
 
229
        public static void Main (string[] args) 
 
230
        {
 
231
                // Initialize GObject type system
 
232
                g_type_init ();
 
233
 
 
234
                Beagle.Util.Log.Level = LogLevel.Always; // shhhh... silence
 
235
 
 
236
                if (args.Length == 0 || Array.IndexOf (args, "--help") > -1 || Array.IndexOf (args, "--usage") > -1)
 
237
                        PrintUsageAndExit ();
 
238
 
 
239
                if (Array.IndexOf (args, "--version") > -1) {
 
240
                        VersionFu.PrintVersion ();
 
241
                        Environment.Exit (0);
 
242
                }
 
243
 
 
244
                StringBuilder query_str =  new StringBuilder ();
 
245
 
 
246
                query = new Query ();
 
247
 
 
248
                // Parse args
 
249
                int i = 0;
 
250
                string next_arg;
 
251
                while (i < args.Length) {
 
252
                        switch (args [i]) {
 
253
 
 
254
                        case "--verbose":
 
255
                                verbose = true;
 
256
                                break;
 
257
                        case "--cache":
 
258
                                display_cached_text = true;
 
259
                                break;
 
260
                        case "--stats-only":
 
261
                                verbose = true;
 
262
                                display_hits = false;
 
263
                                break;
 
264
                        case "--max-hits":
 
265
                                if (++i >= args.Length) PrintUsageAndExit ();
 
266
                                query.MaxHits = Int32.Parse (args[i]);
 
267
                                break;
 
268
 
 
269
                        case "--list-backends":
 
270
                                Console.WriteLine ("Current available backends:");
 
271
                                Console.Write (QueryDriver.ListBackends ());
 
272
                                Environment.Exit (0);
 
273
                                break;
 
274
 
 
275
                        case "--backend":
 
276
                                if (++i >= args.Length) PrintUsageAndExit ();
 
277
 
 
278
                                next_arg = args [i];
 
279
                                if (next_arg.StartsWith ("--")) {
 
280
                                        Console.WriteLine ("--backend requires a backend name. Invalid name '{0}'", next_arg);
 
281
                                        Environment.Exit (1);
 
282
                                        break;
 
283
                                }
 
284
 
 
285
                                if (next_arg [0] != '+' && next_arg [0] != '-')
 
286
                                        QueryDriver.OnlyAllow (next_arg);
 
287
                                else {
 
288
                                        if (next_arg [0] == '+')
 
289
                                                QueryDriver.Allow (next_arg.Substring (1));
 
290
                                        else
 
291
                                                QueryDriver.Deny (next_arg.Substring (1));
 
292
                                }
 
293
 
 
294
                                break;
 
295
 
 
296
                        case "--add-static-backend": 
 
297
                                if (++i >= args.Length) PrintUsageAndExit ();
 
298
 
 
299
                                next_arg = args [i];
 
300
                                if (! next_arg.StartsWith ("--"))
 
301
                                        QueryDriver.AddStaticQueryable (next_arg);
 
302
                                break;
 
303
 
 
304
                        case "--keywords":
 
305
                                PropertyKeywordFu.ReadKeywordMappings ();
 
306
 
 
307
                                Console.WriteLine ("Supported query keywords are:");
 
308
 
 
309
                                foreach (string key in PropertyKeywordFu.Keys) {
 
310
                                        foreach (QueryKeywordMapping mapping in PropertyKeywordFu.Properties (key)) {
 
311
                                                // Dont print properties without description; they confuse people
 
312
                                                if (string.IsNullOrEmpty (mapping.Description))
 
313
                                                        continue;
 
314
                                                Console.WriteLine ("  {0,-20} for {1}", key, mapping.Description);
 
315
                                        }
 
316
                                }
 
317
 
 
318
                                System.Environment.Exit (0);
 
319
                                break;
 
320
 
 
321
                        default:
 
322
                                if (args [i].StartsWith ("--"))
 
323
                                        PrintUsageAndExit ();
 
324
                                if (query_str.Length > 0)
 
325
                                        query_str.Append (' ');
 
326
                                query_str.Append (args [i]);
 
327
                                
 
328
                                break;
 
329
                        }
 
330
 
 
331
                        ++i;
 
332
                }
 
333
 
 
334
                if (verbose)
 
335
                        Beagle.Util.Log.Level = LogLevel.Debug;
 
336
 
 
337
                if (query_str.Length > 0)
 
338
                        query.AddText (query_str.ToString ());
 
339
 
 
340
                Stopwatch watch = new Stopwatch ();
 
341
                watch.Start ();
 
342
                StartQueryDriver ();
 
343
                watch.Stop ();
 
344
                if (verbose)
 
345
                        Console.WriteLine ("QueryDriver started in {0}", watch);
 
346
 
 
347
                QueryResult result = new QueryResult ();
 
348
                result.HitsAddedEvent += OnHitsAdded;
 
349
                result.FinishedEvent += OnFinished;
 
350
 
 
351
                queryStartTime = DateTime.Now;
 
352
                QueryDriver.DoQueryLocal (query, result);
 
353
 
 
354
        }
 
355
 
 
356
        private static void StartQueryDriver ()
 
357
        {
 
358
                try {
 
359
                        string tmp = PathFinder.StorageDir;
 
360
                        if (! Directory.Exists (tmp))
 
361
                                throw new IOException ("Beagle directory not found");
 
362
                } catch (Exception e) {
 
363
                        Console.WriteLine ("Unable to start the daemon: {0}", e.Message);
 
364
                        Environment.Exit (-1);
 
365
                }
 
366
 
 
367
                QueryDriver.IndexingDelay = -1;
 
368
 
 
369
                if (verbose) {
 
370
                        Console.WriteLine ("Starting Beagle Daemon (version {0})", ExternalStringsHack.Version);
 
371
                        Console.WriteLine ("Running on {0}", SystemInformation.MonoRuntimeVersion);
 
372
                }
 
373
 
 
374
                // Check if global configuration files are installed
 
375
                if (! Conf.CheckGlobalConfig ()) {
 
376
                        Console.WriteLine ("Global configuration files not found in '{0}'", PathFinder.ConfigDataDir);
 
377
                        Environment.Exit (-1);
 
378
                }
 
379
 
 
380
                QueryDriver.Init ();
 
381
                QueryDriver.Start ();
 
382
        }
 
383
}