git-svn-id: svn://euphorik.ch/pompage@45 02bbb61a-6d21-0410-aba0-cb053bdfd66a
[pompage.git] / xpi / components / handleProtocol.js
1 // voir : http://www.nexgenmedia.net/docs/protocol/
2
3 // le composant pour cette extension
4 const DIVXPROT_HANDLER_CONTRACTID = "@mozilla.org/network/protocol;1?name=divx";
5 const DIVXPROT_HANDLER_CID = Components.ID("{65aa548e-1dda-11dc-8314-0800200c9a66}");
6
7 // les composants utilisés
8 const URI_CONTRACTID = "@mozilla.org/network/simple-uri;1";
9 const kIOSERVICE_CONTRACTID = "@mozilla.org/network/io-service;1";
10
11 // les interfaces utilisées
12 const nsIProtocolHandler = Components.interfaces.nsIProtocolHandler;
13 const nsIURI = Components.interfaces.nsIURI;
14 const nsISupports = Components.interfaces.nsISupports;
15 const nsIIOService = Components.interfaces.nsIIOService;
16
17
18 /******* COPIER-COLLER de pref.js dans /chrome/content *******/
19 /******* TODO : trouver un moyen d'inclure pref.js *******/
20 function divxlistGetPreferencesService()
21 {
22 return Components.classes["@mozilla.org/preferences-service;1"].getService(Components.interfaces.nsIPrefService).getBranch("");
23 }
24 function divxlistGetRoot()
25 {
26 return divxlistGetPreferencesService().getCharPref("divxlist.root");
27 }
28 function divxlistSetRoot(root)
29 {
30 return divxlistGetPreferencesService().setCharPref("divxlist.root", root);
31 }
32 function divxlistGetCommandes()
33 {
34 var commandes = divxlistGetPreferencesService().getCharPref("divxlist.commandes");
35 var regex = /'[^']*'/g
36 var res = commandes.match(regex);
37 var commandesTab = new Array()
38 if (res != null)
39 for(var i = 0; i < res.length; i += 2)
40 {
41 var motifCommande = new Array(2);
42 motifCommande[0] = res[i].slice(1, res[i].length-1)
43 motifCommande[1] = res[i+1].slice(1, res[i+1].length-1)
44 commandesTab.push(motifCommande);
45 }
46 return commandesTab;
47 }
48 function divxlistSetCommandes(commandes)
49 {
50 var commandesStr = "{"
51 for (var i = 0; i < commandes.length; i++)
52 {
53 if (i != 0) commandesStr += ", "
54 commandesStr += "'" + commandes[i][0] + "' => "
55 commandesStr += "'" + commandes[i][1] + "'"
56 }
57 commandesStr += "}"
58
59 return divxlistGetPreferencesService().setCharPref("divxlist.commandes", commandesStr);
60 }
61
62 /**
63 * Classe ProtocolHandler.
64 */
65 function DivxProtocolHandler(scheme)
66 {
67 this.scheme = scheme;
68 }
69
70 // attributs par défaut
71 DivxProtocolHandler.prototype.defaultPort = -1;
72 DivxProtocolHandler.prototype.protocolFlags = nsIProtocolHandler.URI_NORELATIVE;
73
74 /**
75 * est-ce qu'un port est autorisé
76 */
77 DivxProtocolHandler.prototype.allowPort = function(aPort, aScheme)
78 {
79 return false;
80 }
81
82 /**
83 * Renvoie le nouvel URI.
84 */
85 DivxProtocolHandler.prototype.newURI = function(aSpec, aCharset, aBaseURI)
86 {
87 var uri = Components.classes[URI_CONTRACTID].createInstance(nsIURI);
88 uri.spec = aSpec;
89 return uri;
90 }
91
92 /**
93 * Renvoie le nouveau channel.
94 */
95 DivxProtocolHandler.prototype.newChannel = function(aURI)
96 {
97 var chemin = aURI.spec;
98
99 // détermine quel commande utilisé en comparant le motif et le nom du fichier
100 var commandes = divxlistGetCommandes();
101 var commande;
102 for (var i = 0; i < commandes.length; i++)
103 {
104 var regexp = new RegExp(commandes[i][0], "i");
105 if (regexp.test(chemin))
106 {
107 commande = commandes[i][1]
108 break;
109 }
110 }
111
112 // ajoute le chemin (spécifié dans les options)
113 var root = divxlistGetRoot();
114 // décodage UTF8->latin1 : http://ecmanaut.blogspot.com/2006/07/encoding-decoding-utf8-in-javascript.html
115 chemin = decodeURIComponent(chemin.replace("divx://", root + "/"))
116
117 // extrait le chemin de l'application de la commande
118 // puis l'enlève de la commande
119 var application;
120 var regexp = /^\s*"([^"]+)"\s*/;
121 var res = regexp.exec(commande);
122 if (res == null)
123 {
124 regexp = /^\s*(\S+)\s*/;
125 res = regexp.exec(commande);
126 }
127 application = res[1]
128 commande = commande.replace(regexp, "");
129
130 // sépare les paramètres restant, %f est remplacé par le chemin du fichier
131 var parametres = commande.split(' ');
132 for (var i = 0; i < parametres.length; i++)
133 {
134 parametres[i] = parametres[i].replace("%f", chemin)
135 }
136
137 // crée un nouveau fichier
138 var file = Components.classes["@mozilla.org/file/local;1"].createInstance(Components.interfaces.nsILocalFile);
139 file.initWithPath(application);
140
141 // crée un nouveau processus
142 var process = Components.classes["@mozilla.org/process/util;1"].createInstance(Components.interfaces.nsIProcess);
143 process.init(file);
144
145 // lance le processus. false pour ne pas être blockant
146 process.run(false, parametres, parametres.length);
147
148 // trouver une méthode plus simple pour qu'il ne fasse rien..
149 var finalURL = ""
150 var ios = Components.classes[kIOSERVICE_CONTRACTID].getService(nsIIOService);
151 return ios.newChannel("javascript:document.location='" + finalURL + "'", null, null);
152 }
153
154 /**
155 * Classe DivxProtocolHandlerFactory.
156 */
157 function DivxProtocolHandlerFactory(scheme)
158 {
159 this.scheme = scheme;
160 }
161
162 /**
163 * Méthode permettant la création d'objet de type 'DivxProtocolHandler'.
164 */
165 DivxProtocolHandlerFactory.prototype.createInstance = function(outer, iid)
166 {
167 if(outer != null) throw Components.results.NS_ERROR_NO_AGGREGATION;
168
169 if(!iid.equals(nsIProtocolHandler) && !iid.equals(nsISupports))
170 throw Components.results.NS_ERROR_INVALID_ARG;
171
172 return new DivxProtocolHandler(this.scheme);
173 }
174
175 // la factory
176 var factory_divx = new DivxProtocolHandlerFactory("divx");
177
178 /**
179 * Notre module.
180 */
181 var DIVXModule = new Object();
182
183 /**
184 * Appelé lors de l'enregistrement du module.
185 */
186 DIVXModule.registerSelf = function(compMgr, fileSpec, location, type)
187 {
188 compMgr = compMgr.QueryInterface(Components.interfaces.nsIComponentRegistrar);
189
190 // on enregistre le protocole handler
191 compMgr.registerFactoryLocation(DIVXPROT_HANDLER_CID,
192 "divx",
193 DIVXPROT_HANDLER_CONTRACTID,
194 fileSpec, location, type);
195 }
196
197 /**
198 * Appelé lors du déchargement du module.
199 */
200 DIVXModule.unregisterSelf = function(compMgr, fileSpec, location)
201 {
202 compMgr = compMgr.QueryInterface(Components.interfaces.nsIComponentRegistrar);
203
204 // on dés-enregistre notre protocole handler
205 compMgr.unregisterFactoryLocation(DIVXPROT_HANDLER_CID, fileSpec);
206 }
207
208 /**
209 * Demande la factory pour construire le protocole handler.
210 */
211 DIVXModule.getClassObject = function(compMgr, cid, iid)
212 {
213 if(!iid.equals(Components.interfaces.nsIFactory))
214 throw Components.results.NS_ERROR_NOT_IMPLEMENTED;
215
216 if(cid.equals(DIVXPROT_HANDLER_CID)) return factory_divx;
217
218 throw Components.results.NS_ERROR_NO_INTERFACE;
219 }
220
221 /**
222 * Est-ce que le module peut être déchargé
223 */
224 DIVXModule.canUnload = function(compMgr)
225 {
226 return true;
227 }
228
229 /**
230 * Le point d'entré, retourne le module.
231 */
232 function NSGetModule(compMgr, fileSpec)
233 {
234 return DIVXModule;
235 }