www

Unnamed repository; edit this file 'description' to name the repository.
Log | Files | Refs | Submodules | README | LICENSE

commit 8fe9c5e9e7753a2d74a163666ac2e3f4965d865f
parent 84fcd7d4b8c7cd01add2d694885464a8731b3829
Author: Simon Kornblith <simon@simonster.com>
Date:   Sun,  1 Aug 2010 20:10:18 +0000

closes #1684, checkbox to temporarily disable proxy code
also adds a parameter to disable proxy redirection by domain (although if I had known how much work would be involved in implementing this before I started, I wouldn't have bothered)


Diffstat:
Mchrome/content/zotero/preferences/preferences.js | 25++++++++++++++++++-------
Mchrome/content/zotero/preferences/preferences.xul | 13+++++++++++--
Mchrome/content/zotero/xpcom/proxy.js | 165+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++------
Mchrome/locale/en-US/zotero/preferences.dtd | 4+++-
Mdefaults/preferences/zotero.js | 7++++++-
5 files changed, 191 insertions(+), 23 deletions(-)

diff --git a/chrome/content/zotero/preferences/preferences.js b/chrome/content/zotero/preferences/preferences.js @@ -1769,17 +1769,28 @@ function refreshProxyList() { document.getElementById('proxyTree').currentIndex = -1; document.getElementById('proxyTree-delete').disabled = true; document.getElementById('zotero-proxies-transparent').checked = Zotero.Prefs.get("proxies.transparent"); + document.getElementById('zotero-proxies-autoRecognize').checked = Zotero.Prefs.get("proxies.autoRecognize"); + document.getElementById('zotero-proxies-disableByDomain-checkbox').checked = Zotero.Prefs.get("proxies.disableByDomain"); + document.getElementById('zotero-proxies-disableByDomain-textbox').value = Zotero.Prefs.get("proxies.disableByDomainString"); } /** * Updates proxy autoRecognize and transparent settings based on checkboxes */ function updateProxyPrefs() { - Zotero.Prefs.set("proxies.transparent", document.getElementById('zotero-proxies-transparent').checked); - - var oldTransparent = Zotero.Prefs.get("proxies.transparent"); - var newTransparent = document.getElementById('zotero-proxies-transparent').checked; - Zotero.Prefs.set("proxies.transparent", newTransparent); - - Zotero.Proxies.init() + var transparent = document.getElementById('zotero-proxies-transparent').checked; + Zotero.Prefs.set("proxies.transparent", transparent); + Zotero.Prefs.set("proxies.autoRecognize", document.getElementById('zotero-proxies-autoRecognize').checked); + Zotero.Prefs.set("proxies.disableByDomainString", document.getElementById('zotero-proxies-disableByDomain-textbox').value); + Zotero.Prefs.set("proxies.disableByDomain", document.getElementById('zotero-proxies-disableByDomain-checkbox').checked && + document.getElementById('zotero-proxies-disableByDomain-textbox').value != ""); + + Zotero.Proxies.init(); + + document.getElementById('proxyTree-add').disabled = + document.getElementById('proxyTree-delete').disabled = + document.getElementById('proxyTree').disabled = + document.getElementById('zotero-proxies-autoRecognize').disabled = + document.getElementById('zotero-proxies-disableByDomain-checkbox').disabled = + document.getElementById('zotero-proxies-disableByDomain-textbox').disabled = !transparent; } diff --git a/chrome/content/zotero/preferences/preferences.xul b/chrome/content/zotero/preferences/preferences.xul @@ -613,8 +613,17 @@ To add a new preference: <command id="zotero-proxies-update" oncommand="updateProxyPrefs()"/> <checkbox id="zotero-proxies-transparent" label="&zotero.preferences.proxies.transparent;" command="zotero-proxies-update"/> + <vbox style="margin-left: 1em"> + <checkbox id="zotero-proxies-autoRecognize" label="&zotero.preferences.proxies.autoRecognize;" + command="zotero-proxies-update"/> + <hbox> + <checkbox id="zotero-proxies-disableByDomain-checkbox" label="&zotero.preferences.proxies.disableByDomain;" + command="zotero-proxies-update"/> + <textbox id="zotero-proxies-disableByDomain-textbox" onchange="updateProxyPrefs()"/> + </hbox> + </vbox> - <groupbox flex="1"> + <groupbox flex="1" id="proxyGroup"> <caption label="&zotero.preferences.proxies.configured;"/> <tree flex="1" id="proxyTree" hidecolumnpicker="true" rows="6" seltype="single" @@ -629,7 +638,7 @@ To add a new preference: <separator class="thin"/> <hbox pack="end"> <button disabled="true" id="proxyTree-delete" label="-" onclick="deleteProxy()"/> - <button label="+" onclick="showProxyEditor()"/> + <button label="+" id="proxyTree-add" onclick="showProxyEditor()"/> </hbox> </groupbox> diff --git a/chrome/content/zotero/xpcom/proxy.js b/chrome/content/zotero/xpcom/proxy.js @@ -38,9 +38,9 @@ Zotero.Proxies = new function() { var ioService = Components.classes["@mozilla.org/network/io-service;1"] .getService(Components.interfaces.nsIIOService); var windowMediator = Components.classes["@mozilla.org/appshell/window-mediator;1"] - .getService(Components.interfaces.nsIWindowMediator); - var lastRecognizedURI = false; - var lastButton = false; + .getService(Components.interfaces.nsIWindowMediator); + var myHostName = null; + var myCanonicalHostName = null; /** * Initializes http-on-examine-response observer to intercept page loads and gets preferences @@ -61,12 +61,18 @@ Zotero.Proxies = new function() { } Zotero.Proxies.transparent = Zotero.Prefs.get("proxies.transparent"); + Zotero.Proxies.autoRecognize = Zotero.Proxies.transparent && Zotero.Prefs.get("proxies.autoRecognize"); + + var disableByDomainPref = Zotero.Prefs.get("proxies.disableByDomain"); + Zotero.Proxies.disableByDomain = (Zotero.Proxies.transparent && disableByDomainPref ? Zotero.Prefs.get("proxies.disableByDomainString") : null); + + Zotero.Proxies.lastIPCheck = 0; + Zotero.Proxies.lastIPs = ""; + Zotero.Proxies.disabledByDomain = false; } /** * Observe method to capture page loads and determine if they're going through an EZProxy. - * At the moment, also clears Content-Disposition header on requests for EndNote files so we - * can capture them instead of letting them get saved as attachments * * @param {nsIChannel} channel */ @@ -113,11 +119,17 @@ Zotero.Proxies = new function() { var bw = _getBrowserAndWindow(channel.notificationCallbacks); if(!bw) return; - _showNotification(bw, - Zotero.getString('proxies.notification.recognized.label', [proxy.hosts[0], channel.URI.hostPort]), - "enable", function() { _showDialog(proxy.hosts[0], channel.URI.hostPort, proxy) }); + + var savedTransparent = false; + if(Zotero.Proxies.autoRecognize) { + // Ask to save only if automatic proxy recognition is on + savedTransparent = _showNotification(bw, + Zotero.getString('proxies.notification.recognized.label', [proxy.hosts[0], channel.URI.hostPort]), + "enable", function() { _showDialog(proxy.hosts[0], channel.URI.hostPort, proxy) }); + } proxy.save(); + break; } } @@ -132,9 +144,35 @@ Zotero.Proxies = new function() { if(!docShell.allowMetaRedirects) return; + // check that proxy redirection is actually enabled + if(!Zotero.Proxies.transparent) return; + var proxied = Zotero.Proxies.properToProxy(url, true); if(!proxied) return; + if(Zotero.Proxies.disableByDomain) { + var now = new Date(); + + // IP update interval is every 15 minutes + if((now - Zotero.Proxies.lastIPCheck) > 900000) { + Zotero.debug("Proxies: Retrieving IPs"); + var ips = Zotero.Proxies.DNS.getIPs(); + var ipString = ips.join(","); + if(ipString != Zotero.Proxies.lastIPs) { + // if IPs have changed, run reverse lookup + Zotero.Proxies.lastIPs = ipString; + // TODO IPv6 + var domains = [Zotero.Proxies.DNS.reverseLookup(ip) for each(ip in ips) if(ip.indexOf(":") == -1)]; + + // if domains necessitate disabling, disable them + Zotero.Proxies.disabledByDomain = domains.join(",").indexOf(Zotero.Proxies.disableByDomain) != -1; + } + } + + Zotero.Proxies.lastIPCheck = now; + if(Zotero.Proxies.disabledByDomain) return; + } + // try to find a corresponding browser object var bw = _getBrowserAndWindow(channel.notificationCallbacks); if(!bw) return; @@ -344,8 +382,8 @@ Zotero.Proxies = new function() { // disable transparent if checkbox checked if(io.disable) { - Zotero.Proxies.transparent = false; - Zotero.Prefs.set("proxies.transparent", false); + Zotero.Proxies.autoRecognize = false; + Zotero.Prefs.set("proxies.autoRecognize", false); } if(io.add) { @@ -827,4 +865,107 @@ Zotero.Proxies.Detectors.Juniper = function(channel) { proxy.scheme = m[1]+"/%d"+",DanaInfo=%h%a+%f"; proxy.hosts = [m[3]]; return proxy; -} -\ No newline at end of file +} + +Zotero.Proxies.DNS = new function() { + var _callbacks = []; + + this.getIPs = function() { + var dns = Components.classes["@mozilla.org/network/dns-service;1"] + .getService(Components.interfaces.nsIDNSService); + myHostName = dns.myHostName; + var record = dns.resolve(myHostName, null); + + // get IPs + var ips = []; + while(record.hasMore()) { + ips.push(record.getNextAddrAsString()); + } + + return ips; + } + + this.reverseLookup = function(ip) { + Zotero.debug("Proxies: Performing reverse lookup for IP "+ip); + + // build DNS query + var bytes = Zotero.randomString(2)+"\x01\x00\x00\x01\x00\x00\x00\x00\x00\x00"; + + var ipParts = ip.split("."); + ipParts.reverse(); + for each(var ipPart in ipParts) { + bytes += String.fromCharCode(ipPart.length); + bytes += ipPart; + } + for each(var subdomain in ["in-addr", "arpa"]) { + bytes += String.fromCharCode(subdomain.length); + bytes += subdomain; + } + bytes += "\x00\x00\x0c\x00\x01"; + + var sts = Components.classes["@mozilla.org/network/socket-transport-service;1"] + .getService(Components.interfaces.nsISocketTransportService); + var transport = sts.createTransport(["udp"], 1, "8.8.8.8", 53, null); + var rawinStream = transport.openInputStream(Components.interfaces.nsITransport.OPEN_BLOCKING, null, null); + var rawoutStream = transport.openOutputStream(Components.interfaces.nsITransport.OPEN_BLOCKING, null, null); + + var outStream = Components.classes["@mozilla.org/binaryoutputstream;1"] + .createInstance(Components.interfaces.nsIBinaryOutputStream); + outStream.setOutputStream(rawoutStream); + outStream.writeBytes(bytes, bytes.length); + outStream.close(); + + Zotero.debug("Proxies: Sent reverse lookup request"); + + var inStream = Components.classes["@mozilla.org/binaryinputstream;1"] + .createInstance(Components.interfaces.nsIBinaryInputStream); + var sinStream = Components.classes["@mozilla.org/scriptableinputstream;1"] + .createInstance(Components.interfaces.nsIScriptableInputStream); + inStream.setInputStream(rawinStream); + sinStream.init(rawinStream); + + var stuff = inStream.read32(); + var qdCount = inStream.read16(); + var anCount = inStream.read16(); + var nsCount = inStream.read16(); + var arCount = inStream.read16(); + + // read queries back out + for(var i=0; i<qdCount; i++) { + var len = inStream.read8(); + while(len != 0) { + sinStream.read(len); + len = inStream.read8(); + } + inStream.read16(); // QTYPE + inStream.read16(); // QCLASS + } + + // get reverse lookup domains + var domain = []; + if(anCount == 1) { + inStream.read16(); // HOST + inStream.read16(); // TYPE + inStream.read16(); // CLASS + inStream.read32(); // TTL + var rdLength = inStream.read16(); // RDLENGTH + var bc = 0; + domain = []; + while(bc < rdLength) { + bc += 1; + if(bc > rdLength) break; + var len = inStream.read8(); + bc += len; + if(bc > rdLength) break; + domain.push(sinStream.read(len)); + } + domain.pop(); + } + + domain = domain.join("."); + Zotero.debug("Proxies: "+ip+" PTR "+domain); + + inStream.close(); + return domain; + } +}; +\ No newline at end of file diff --git a/chrome/locale/en-US/zotero/preferences.dtd b/chrome/locale/en-US/zotero/preferences.dtd @@ -124,7 +124,9 @@ <!ENTITY zotero.preferences.proxies.desc_before_link "Zotero will transparently redirect requests through saved proxies. See the"> <!ENTITY zotero.preferences.proxies.desc_link "proxy documentation"> <!ENTITY zotero.preferences.proxies.desc_after_link "for more information."> -<!ENTITY zotero.preferences.proxies.transparent "Automatically remember proxied resources"> +<!ENTITY zotero.preferences.proxies.transparent "Enable proxy redirection"> +<!ENTITY zotero.preferences.proxies.autoRecognize "Automatically recognize proxied resources"> +<!ENTITY zotero.preferences.proxies.disableByDomain "Disable proxy redirection when my domain name contains "> <!ENTITY zotero.preferences.proxies.configured "Configured Proxies"> <!ENTITY zotero.preferences.proxies.hostname "Hostname"> <!ENTITY zotero.preferences.proxies.scheme "Scheme"> diff --git a/defaults/preferences/zotero.js b/defaults/preferences/zotero.js @@ -104,7 +104,9 @@ pref("extensions.zotero.export.quickCopy.compatibility.word", false); // Integration settings pref("extensions.zotero.integration.port", 50001); pref("extensions.zotero.integration.autoRegenerate", -1); // -1 = ask; 0 = no; 1 = yes -pref("extensions.zotero.integration.realWindow", false); + +// Connector settings +pref("extensions.zotero.connector.port", 23119); // ascii "ZO" // Zeroconf pref("extensions.zotero.zeroconf.server.enabled", false); @@ -133,7 +135,10 @@ pref("extensions.zotero.sync.storage.deleteDelayDays", 30); pref("extensions.zotero.sync.storage.groups.enabled", true); // Proxy +pref("extensions.zotero.proxies.autoRecognize", true); pref("extensions.zotero.proxies.transparent", true); +pref("extensions.zotero.proxies.disableByDomain", false); +pref("extensions.zotero.proxies.disableByDomainString", ".edu"); // Data layer purging pref("extensions.zotero.purge.creators", false);