view-as-mime-type: fix bug in interactive declaration
[conkeror.git] / modules / gitweb-webjump.js
blobe235c0ef51d65396af7bfb7b6586df469cfdb3ac
1 /**
2  * (C) Copyright 2009 David Kettler
3  *
4  * Use, modification, and distribution are subject to the terms specified in the
5  * COPYING file.
6  *
7  * Construct a webjump (with completer) to visit repository summary
8  * pages at a gitweb server.
9 **/
11 require("webjump.js");
13 /* OPML files for completion on webjumps. */
14 gitweb_webjumps_opml = {};
16 define_variable("gitweb_webjumps_opml_directory", null,
17                 "A directory for storing the OPML data corresponding to a " +
18                 "gitweb webjump; the data can be fetched using " +
19                 "gitweb-webjump-get-opml.  " +
20                 "If the data is available for a webjump then it will provide " +
21                 "completions for the available repositories.");
24 function parse_gitweb_completions_from_dom_node(doc) {
25     let elems = doc.getElementsByTagName("outline");
27     let completions = [];
28     for (let i = 0; i < elems.length; ++i) {
29         let node = elems[i];
30         let type = node.getAttribute("type");
31         let name = node.getAttribute("text");
32         if (type == "rss" && name)
33             completions.push(name.replace(/\.git$/, ""));
34     }
35     completions.sort();
37     return completions;
41 function gitweb_webjump_get_completions_from_file(file) {
42     var file_istream = Cc["@mozilla.org/network/file-input-stream;1"]
43         .createInstance(Ci.nsIFileInputStream);
44     file_istream.init(file, MODE_RDONLY, 0644, false);
45     var dom_parser = Cc["@mozilla.org/xmlextras/domparser;1"]
46         .createInstance(Ci.nsIDOMParser);
47     var doc = dom_parser.parseFromStream(file_istream, "UTF-8",
48                                          file.fileSize, "text/xml");
50     return parse_gitweb_completions_from_dom_node(doc);
54 /**
55  * A completer that gets the list of repositories from the gitweb
56  * generated OPML.
57  */
58 function gitweb_webjump_completer(opml_file) {
59     let completions = null;
60     let file_time = 0;
62     return function (input, pos, conservative) {
63         if (pos == 0 && conservative)
64             yield co_return(undefined);
65         let str = input.substring(0,pos);
67         if (opml_file.exists() && opml_file.lastModifiedTime > file_time) {
68             file_time = opml_file.lastModifiedTime;
69             completions = gitweb_webjump_get_completions_from_file(opml_file);
70         }
71         if (!completions)
72             yield co_return(null);
74         let words = trim_whitespace(input.toLowerCase()).split(/\s+/);
75         let data = completions.filter(function (x) {
76             for (var i = 0; i < words.length; ++i)
77                 if (x.toLowerCase().indexOf(words[i]) == -1)
78                     return false;
79             return true;
80         });
82         let c = {count: data.length,
83                  get_string: function (i) data[i],
84                  get_description: function (i) data[i],
85                  get_input_state: function (i) [data[i]]};
86         yield co_return(c);
87     };
91 /* buffer is used only to associate with the download */
92 define_keywords("$buffer");
93 function gitweb_webjump_get_opml(key) {
94     keywords(arguments);
95     let opml = gitweb_webjumps_opml[key];
96     if (!opml)
97         return null;
98     save_uri(load_spec(opml.url), opml.file,
99              $buffer = arguments.$buffer, $use_cache = false,
100              $temp_file = true);
101     return opml;
104 interactive("gitweb-webjump-get-opml",
105             "Fetch the OPML data corresponding to a gitweb webjump from " +
106             "the gitweb server and make it available to the gitweb webjump " +
107             "completer.",
108             function (I) {
109                 var completions = [];
110                 for (let i in gitweb_webjumps_opml)
111                     completions.push(i);
112                 completions.sort();
113                 var key = yield I.minibuffer.read(
114                     $prompt = "Get OPML for gitweb webjump:",
115                     $history = "webjump",
116                     $completer = all_word_completer($completions = completions),
117                     $match_required = true);
118                 gitweb_webjump_get_opml(key, $buffer = I.buffer);
119             });
123  * Construct a webjump to visit repository summary pages at a gitweb
124  * server.
126  * If a repository name is supplied as $default then the alternative
127  * url is set to that repository at the gitweb site.  If an
128  * alternative is not specified by either $default or $alternative
129  * then it is set to the repository list page of the gitweb site.
131  * A completer is provided that uses the list of repositories from the
132  * OPML data on the gitweb server.  A local file for the OPML data
133  * must be specified either with $opml_file or via
134  * gitweb_webjumps_opml_directory.  The OPML data must be manually
135  * downloaded; eg. using gitweb-webjump-get-opml.  Each time the
136  * completer is used it will check if the file has been updated and
137  * reload if necessary.
139  * A completer may instead be specified with $completer.
140  */
141 define_keywords("$default", "$alternative", "$completer", "$opml_file");
142 function define_gitweb_summary_webjump(key, base_url) {
143     keywords(arguments);
144     let completer = arguments.$completer;
145     let alternative = arguments.$alternative;
146     let gitweb_url = base_url + "/gitweb.cgi";
147     let summary_url = gitweb_url + "?p=%s.git;a=summary";
148     let opml_url = gitweb_url + "?a=opml";
150     let opml_file = arguments.$opml_file;
151     if (typeof opml_file == 'string')
152         opml_file = make_file(opml_file);
153     if (!opml_file && gitweb_webjumps_opml_directory) {
154         opml_file = Cc["@mozilla.org/file/local;1"]
155             .createInstance(Ci.nsILocalFile);
156         if (gitweb_webjumps_opml_directory instanceof Ci.nsILocalFile)
157             opml_file.initWithFile(gitweb_webjumps_opml_directory);
158         else
159             opml_file.initWithPath(gitweb_webjumps_opml_directory);
160         opml_file.appendRelativePath(key + ".opml");
161     }
163     if (!completer && opml_file) {
164         completer = gitweb_webjump_completer(opml_file);
165         gitweb_webjumps_opml[key] = {file: opml_file, url: opml_url};
166     }
167     if (arguments.$default)
168         alternative = summary_url.replace("%s", arguments.$default);
169     if (!alternative)
170         alternative = gitweb_url;
172     define_webjump(key, summary_url,
173                    $completer = completer,
174                    $alternative = alternative);