diff --git a/CHANGELOG.md b/CHANGELOG.md index 545cb67..14202d0 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,10 @@ # Change Log +## 4.0.0 - 2020-11-10 +- Support for Thunderbird 78.* +- Complete rewrite of code structure + - (thanks to Jürgen Ernst and his [Display mail user agent](https://addons.thunderbird.net/ja/thunderbird/addon/display-mail-user-agent-t/) for some direction) + ## 3.8.0 - 2020-06-02 ### Added diff --git a/README.md b/README.md index a972a44..8eeff38 100644 --- a/README.md +++ b/README.md @@ -13,7 +13,7 @@ MailHops is an email route API. It does a few things: ### MailHops Message View - + ### MailHops Route Map @@ -21,7 +21,7 @@ MailHops is an email route API. It does a few things: ### MailHops Options - + ### MailHops Dashboard diff --git a/build.sh b/build.sh index 840695a..4d4f73b 100755 --- a/build.sh +++ b/build.sh @@ -4,4 +4,4 @@ filename='mailhops' rm -f $filename.zip -zip -r $filename.zip ./ -x ./images/* -i *.js *.xul *.png *.gif *.css *.json *.dtd _locales/*/messages.json *.manifest +zip -r $filename.zip ./ -i *.js *.xhtml *.html *.png *.svg *.gif *.css *.json _locales/*/messages.json diff --git a/chrome.manifest b/chrome.manifest deleted file mode 100644 index 918e31a..0000000 --- a/chrome.manifest +++ /dev/null @@ -1,16 +0,0 @@ -content mailhops chrome/content/ - -skin mailhops classic/1.0 chrome/skin/classic/ - -locale mailhops de chrome/locale/de/ -locale mailhops en chrome/locale/en/ -locale mailhops es chrome/locale/es/ -locale mailhops fr chrome/locale/fr/ -locale mailhops ja chrome/locale/ja/ -locale mailhops pl chrome/locale/pl/ -locale mailhops pt-BR chrome/locale/pt-BR/ -locale mailhops ru chrome/locale/ru/ -locale mailhops zh-CN chrome/locale/zh-CN/ - -overlay chrome://messenger/content/messenger.xul chrome://mailhops/content/msgNotificationBar.xul -overlay chrome://messenger/content/messenger.xul chrome://mailhops/content/msgListColumn.xul \ No newline at end of file diff --git a/chrome/content/mailhops-2-msgNotificationBar.js b/chrome/content/mailhops-2-msgNotificationBar.js deleted file mode 100644 index 0e34d8f..0000000 --- a/chrome/content/mailhops-2-msgNotificationBar.js +++ /dev/null @@ -1,444 +0,0 @@ -var mailHopsDisplay = -{ - resultBox: null, - resultText: null, - resultDetails: null, - mailhopsDataPaneHops: null, - mailhopsDataPaneSPF: null, - mailhopsDataPaneDKIM: null, - mailhopsDataPaneMailer: null, - mailhopsDataPaneDNSBL: null, - mailhopsResultWeather: null, - mailhopsUnsubscribe: null, - mailHopsAccountMessage: null, - mhBox: null, - options: null, - - init: function(options, reload){ - - this.options = options; - this.mhBox = document.getElementById("mailhopsNoficationBox"); - this.mhNoteBox = document.getElementById("mailhopsNotification"); - this.resultBox = document.getElementById("mailhopsResult"); - this.resultText = document.getElementById("mailhopsResultText"); - this.mailhopsResultWeather = document.getElementById("mailhopsResultWeather"); - this.mailhopsUnsubscribe = document.getElementById("mailhopsUnsubscribe"); - this.resultDetails = document.getElementById("mailhopsDataPaneDetails"); - this.mailHopsAccountMessage = document.getElementById("mailHopsAccountMessage"); - this.mailhopsDataPaneHops = document.getElementById("mailhopsDataPaneHops"); - - //auth - this.mailhopsDataPaneSPF = document.getElementById("mailhopsDataPaneSPF"); - this.mailhopsDataPaneDKIM = document.getElementById("mailhopsDataPaneDKIM"); - this.mailhopsDataPaneMailer = document.getElementById("mailhopsDataPaneMailer"); - this.mailhopsDataPaneDNSBL = document.getElementById("mailhopsDataPaneDNSBL"); - - //wait for message to be selected before showing - if (!reload && this.mhBox) - this.mhBox.style.display = 'none'; - - //event listner for route click to launch map - this.mailhopsDataPaneDNSBL.addEventListener("click", function () { - if(this.hasAttribute('data-ip')) - mailHopsUtils.launchSpamHausURL( this.getAttribute('data-ip') ); - }); - - this.resultText.addEventListener("click", function () { - if(this.value.indexOf('Rate Limit')!==-1) - window.openDialog("chrome://mailhops/content/preferences.xul","","chrome, dialog, modal, centerscreen").focus(); - else if(this.hasAttribute('data-route')) - mailHopsUtils.launchMap( String(this.getAttribute('data-route')), options ); - }); - - this.mailhopsResultWeather.addEventListener("click", function () { - mailHopsUtils.launchExternalURL(this.getAttribute('href')); - }); - - this.mailHopsAccountMessage.addEventListener("click", function () { - mailHopsUtils.launchExternalURL(this.getAttribute('href')); - this.style.display = 'none'; - }); - - this.mailhopsDataPaneHops.addEventListener("click", function () { - this.parentElement.classList.toggle('active'); - if(mailHopsDisplay.resultDetails.style.display !== 'block') - mailHopsDisplay.resultDetails.style.display = 'block'; - else - mailHopsDisplay.resultDetails.style.display = 'none'; - }); - - this.mailhopsUnsubscribe.addEventListener("click", function () { - if(this.getAttribute('href')) - mailHopsUtils.launchExternalURL(this.getAttribute('href')); - }); - - if(!!options.bar_color) - this.mhNoteBox.style.background = options.bar_color; - else - this.mhNoteBox.style.background = ''; - - if(!!options.font_size) - this.mhNoteBox.style.fontSize = options.font_size; - - if(!!options.font_color){ - this.resultText.style.color = options.font_color; - this.mailhopsResultWeather.style.color = options.font_color; - this.mailhopsUnsubscribe.style.color = options.font_color; - this.mailhopsDataPaneSPF.style.color = options.font_color; - this.mailhopsDataPaneDKIM.style.color = options.font_color; - this.mailhopsDataPaneMailer.style.color = options.font_color; - this.mailhopsDataPaneDNSBL.style.color = options.font_color; - } - }, - - lists: function( header_unsubscribe ){ - - this.mailhopsUnsubscribe.style.display='none'; - - if(header_unsubscribe){ - this.mailhopsUnsubscribe.style.display=''; - var listArr=header_unsubscribe.split(','); - var href=''; - if(listArr.length){ - for(var h=0;h',''); - if(href.indexOf('mailto:')!=-1){ - if(href.toLowerCase().indexOf('subject=')==-1){ - if(href.indexOf('?')==-1) - href+='?subject=Unsubscribe'; - else - href+='&subject=Unsubscribe'; - } - } - this.mailhopsUnsubscribe.setAttribute('href',href); - } - } - } - }, - - auth: function( header_xmailer, header_useragent, header_xmimeole, header_auth, header_spf ){ - //SPF - if(header_spf){ - header_spf=header_spf.replace(/^\s+/,""); - var headerSPFArr=header_spf.split(' '); - this.mailhopsDataPaneSPF.setAttribute('value','SPF: '+headerSPFArr[0]); - this.mailhopsDataPaneSPF.style.backgroundImage = "url('chrome://mailhops/content/images/auth/"+headerSPFArr[0]+".png')"; - this.mailhopsDataPaneSPF.setAttribute('tooltiptext',header_spf+'\n'+mailHopsUtils.spf(headerSPFArr[0])); - this.mailhopsDataPaneSPF.style.display='block'; - } else { - this.mailhopsDataPaneSPF.style.display='none'; - } - //Authentication-Results - //http://tools.ietf.org/html/rfc5451 - if(header_auth){ - var headerAuthArr=header_auth.split(';'); - var dkim_result; - var spf_result; - for(var h=0;h 0) - distanceText = mailHopsUtils.addCommas(Math.round(response.distance.kilometers))+' km traveled'; - else if(response.distance.miles > 0) - distanceText = mailHopsUtils.addCommas(Math.round(response.distance.miles))+' mi traveled'; - } else if(displayText=='') - displayText = ' Local message.'; - } - - if(!!message.time && message.time >= 0){ - message.time = message.time/1000; - if(message.time < 60) - distanceText += ' in '+message.time+' sec.'; - else if(message.time < 3600) //something is wrong if it takes this long - distanceText += ' in '+Math.round(message.time/60)+' min.'; - else //something is wrong if it takes this long - distanceText += ' in '+Math.round(message.time/60/60)+' hr.'; - } - - if(header_route) - this.resultText.setAttribute("data-route", header_route); - else - this.resultText.removeAttribute("data-route"); - - this.resultText.setAttribute('value', displayText+' ( '+distanceText+' )'); - this.resultText.style.backgroundImage = "url('"+image+"')"; - - if(meta && meta.message){ - this.mailHopsAccountMessage.style.display = 'inline'; - if(meta.message.text) - this.mailHopsAccountMessage.value = meta.message.text; - if(meta.message.url) - this.mailHopsAccountMessage.setAttribute('href', meta.message.url); - } else { - this.mailHopsAccountMessage.style.display = 'none'; - } - }, //end route - - toggleMailHopsBar: function(show){ - if(show && this.mhBox.style.display == 'none') - this.mhBox.style.display = ''; - else if(!show && this.mhBox.style.display == '') - this.mhBox.style.display = 'none'; - } -}; diff --git a/chrome/content/mailhops-3.js b/chrome/content/mailhops-3.js deleted file mode 100644 index 43ef8e2..0000000 --- a/chrome/content/mailhops-3.js +++ /dev/null @@ -1,512 +0,0 @@ -/* -* @author: Andrew Van Tassel -* @email: andrew@andrewvantassel.com -* @website: http://mailhops.com -*/ - -var mailHops = { - msgURI: null, - isLoaded: false, - options: { - 'version':'MailHops Plugin 3.8.1', - 'lan':'en', - 'unit':'mi', - 'api_http':'https://', - 'api_host':'api.mailhops.com', - 'debug':false, - 'hide_compact':false, - 'bar_color': '#5E7A9B', - 'font_color': '#ffffff', - 'font_size': '14px', - 'country_tag':false, - 'travel_time_junk':false, - 'country_filter':[] - }, - message: { - secure:[] - ,time: null - } -}; - -mailHops.LOG = function(msg) { - if(!mailHops.options.debug) - return; - var consoleService = Components.classes["@mozilla.org/consoleservice;1"].getService(Components.interfaces.nsIConsoleService); - consoleService.logStringMessage('MailHops: '+msg); -}; - -mailHops.init = function() { - //load preferences - mailHops.loadPref(); - - document.getElementById("mailhopsLogo").addEventListener("click", function () { - window.openDialog("chrome://mailhops/content/preferences.xul","","chrome, dialog, modal, centerscreen").focus(); - }); - - document.getElementById("mailhopsDataPaneRefresh").addEventListener("click", function () { - mailHops.refreshCache(); - }); - - mailHops.isLoaded = true; - -}; - -mailHops.loadPref = function(reload) -{ - mailHops.LOG('load MailHops prefs'); - //get preferences - mailHops.options.lan = mailHops.getCharPref('mail.mailHops.lang','en'); - mailHops.options.unit = mailHops.getCharPref('mail.mailHops.unit','mi'); - mailHops.options.fkey = mailHops.getCharPref('mail.mailHops.fkey','');//forecast.io api_key - - //Display - mailHops.options.bar_color = mailHops.getCharPref('mail.mailHops.bar_color','#5E7A9B'); - - mailHops.options.font_color = mailHops.getCharPref('mail.mailHops.font_color','#ffffff'); - - mailHops.options.font_size = mailHops.getCharPref('mail.mailHops.font_size','14px'); - - mailHops.options.debug = mailHops.getCharPref('mail.mailHops.debug','false')=='true'?true:false; - - mailHops.options.hide_compact = mailHops.getCharPref('mail.mailHops.hide_compact','false')=='true'?true:false; - - mailHops.options.api_host = mailHops.getCharPref('mail.mailHops.api_host','api.mailhops.com'); - - mailHops.options.api_http = mailHops.getCharPref('mail.mailHops.api_http','https://'); - - mailHops.options.api_key = mailHops.getCharPref('mail.mailHops.api_key',''); - - mailHops.options.map_provider = mailHops.getCharPref('mail.mailHops.map_provider','OpenStreetMap.Mapnik'); - - mailHops.options.country_tag = mailHops.getCharPref('mail.mailHops.country_tag','false')=='true'?true:false; - - mailHops.options.travel_time_junk = mailHops.getCharPref('mail.mailHops.travel_time_junk','false')=='true'?true:false; - - mailHops.options.country_filter = mailHops.getCharPref('mail.mailHops.country_filter',[]); - - //init display - mailHopsDisplay.init( mailHops.options, reload ); -}; - -mailHops.StreamListener = -{ - content: "" , - found: false , - onDataAvailable: function ( request, inputStream, offset, count ) - { - try { - var sis = Components.classes["@mozilla.org/scriptableinputstream;1"].createInstance ( Components.interfaces.nsIScriptableInputStream ) ; - sis.init( inputStream ) ; - - if( !this.found ) - { - this.content += sis.read ( count ) ; - this.content = this.content.replace ( /\r/g , "" ) ; - var pos = this.content.indexOf ( "\n\n" ) ; - - if ( pos > -1 ) - { - // last header line must end with LF -> pos+1 !!! - this.content = this.content.substr ( 0 , pos + 1 ) ; - this.found = true ; - } - } - } catch(e) { - //failed to read input stream - mailHops.LOG('StreamListener Error: '+JSON.stringify(e)); - } - }, - onStartRequest: function ( request ) - { - this.content = "" ; - this.found = false ; - }, - onStopRequest: function ( aRequest , aStatusCode ) - { - mailHops.headers = Components.classes["@mozilla.org/messenger/mimeheaders;1"].createInstance ( Components.interfaces.nsIMimeHeaders ) ; - mailHops.headers.initialize(this.content, this.content.length); - mailHops.headerData = this.content; - mailHops.getRoute(); - } -}; - -/** -* loop through the header, find out if we have received-from headers -*/ -mailHops.loadHeaderData = function() { - - if(!!mailHops.options.hide_compact){ - // CompactHeader toggle header logic - var compactHeadersView = document.getElementById('CompactHeader_collapsedHeaderView'); - if(!!compactHeadersView){ - if(compactHeadersView.collapsed===true){ - mailHopsDisplay.toggleMailHopsBar(true); - } else if(compactHeadersView.collapsed===false){ - mailHopsDisplay.toggleMailHopsBar(false); - return; - } - } - } - - var msgURI = null ; - - if ( gDBView ){ - msgURI = gDBView.URIForFirstSelectedMessage; - } - if ( msgURI == null ){ - return; - } - mailHops.msgURI = msgURI; - var messenger = Components.classes["@mozilla.org/messenger;1"].createInstance ( Components.interfaces.nsIMessenger ) ; - var msgService = messenger.messageServiceFromURI ( msgURI ) ; - msgService.CopyMessage ( msgURI , mailHops.StreamListener , false , null , msgWindow , {} ) ; -}; - -mailHops.getRoute = function(){ - //IP regex - var regexIp=/(1\d{0,2}|2(?:[0-4]\d{0,1}|[6789]|5[0-5]?)?|[3-9]\d?|0)\.(1\d{0,2}|2(?:[0-4]\d{0,1}|[6789]|5[0-5]?)?|[3-9]\d?|0)\.(1\d{0,2}|2(?:[0-4]\d{0,1}|[6789]|5[0-5]?)?|[3-9]\d?|0)\.(1\d{0,2}|2(?:[0-4]\d{0,1}|[6789]|5[0-5]?)?|[3-9]\d?|0)(\/(?:[012]\d?|3[012]?|[456789])){0,1}$/; - var regexAllIp = /(1\d{0,2}|2(?:[0-4]\d{0,1}|[6789]|5[0-5]?)?|[3-9]\d?|0)\.(1\d{0,2}|2(?:[0-4]\d{0,1}|[6789]|5[0-5]?)?|[3-9]\d?|0)\.(1\d{0,2}|2(?:[0-4]\d{0,1}|[6789]|5[0-5]?)?|[3-9]\d?|0)\.(1\d{0,2}|2(?:[0-4]\d{0,1}|[6789]|5[0-5]?)?|[3-9]\d?|0)(\/(?:[012]\d?|3[012]?|[456789])){0,1}/g; - var regexIPV6 = /s*((([0-9A-Fa-f]{1,4}:){7}([0-9A-Fa-f]{1,4}|:))|(([0-9A-Fa-f]{1,4}:){6}(:[0-9A-Fa-f]{1,4}|((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3})|:))|(([0-9A-Fa-f]{1,4}:){5}(((:[0-9A-Fa-f]{1,4}){1,2})|:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3})|:))|(([0-9A-Fa-f]{1,4}:){4}(((:[0-9A-Fa-f]{1,4}){1,3})|((:[0-9A-Fa-f]{1,4})?:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){3}(((:[0-9A-Fa-f]{1,4}){1,4})|((:[0-9A-Fa-f]{1,4}){0,2}:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){2}(((:[0-9A-Fa-f]{1,4}){1,5})|((:[0-9A-Fa-f]{1,4}){0,3}:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){1}(((:[0-9A-Fa-f]{1,4}){1,6})|((:[0-9A-Fa-f]{1,4}){0,4}:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:))|(:(((:[0-9A-Fa-f]{1,4}){1,7})|((:[0-9A-Fa-f]{1,4}){0,5}:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:)))(%.+)?s*/g; - - var headReceived = mailHops.headers.extractHeader ( "Received" , true ); - var headDate = mailHops.headers.extractHeader ( "Date" , true ); - var headXReceived = mailHops.headers.extractHeader ( "X-Received" , false ); - var headXOrigIP = mailHops.headers.extractHeader ( "X-Originating-IP" , false ); - // auth box - var headXMailer = mailHops.headers.extractHeader ( "X-Mailer" , false ); - var headUserAgent = mailHops.headers.extractHeader ( "User-Agent" , false ); - var headXMimeOLE = mailHops.headers.extractHeader ( "X-MimeOLE" , false ); - var headReceivedSPF = mailHops.headers.extractHeader ( "Received-SPF" , false ); - var headAuth = mailHops.headers.extractHeader ( "Authentication-Results" , false ); - var headListUnsubscribe = mailHops.headers.extractHeader ( "List-Unsubscribe" , false ) ; - - var all_ips = new Array(); - var rline = '',firstDate=headDate,lastDate; - //empty secure and time - mailHops.message.secure = []; - mailHops.message.time = null; - - mailHopsDisplay.lists( headListUnsubscribe ); - - mailHopsDisplay.auth( headXMailer, headUserAgent, headXMimeOLE, headAuth, headReceivedSPF ); - - //loop through the received headers and parse for IP addresses - if (!!headReceived){ - var received_ips = new Array(); - var headReceivedArr = headReceived.split('\n'); - for( var h=0; h < headReceivedArr.length; h++ ) { - //build the received line by concat until semi-colon ; date/time - rline += headReceivedArr[h]; - if(headReceivedArr[h].indexOf(';') === -1) - continue; - // first and last dates are used to calculate time traveled - if(rline.indexOf(';') !== -1){ - if(!firstDate) - firstDate = rline.substring(rline.indexOf(';')+1).trim(); - if(!lastDate) - lastDate = rline.substring(rline.indexOf(';')+1).trim(); - } - - // IPV6 check - rline = rline.replace(/\[IPv6\:/g,'['); - if(rline.match(regexIPV6)){ - all_ips.unshift( rline.match(regexIPV6)[0] ); - //reset the line - rline=''; - continue; - } - // parse IPs out of Received line - received_ips = rline.match(regexAllIp); - //continue if no IPs found - if(!received_ips){ - //reset the line - rline=''; - continue; - } - //get unique IPs for each Received header - received_ips = received_ips.filter(function(item, pos) { - return received_ips.indexOf(item) === pos; - }); - for( var r=received_ips.length; r >= 0 ; r-- ){ - if(regexIp.test(received_ips[r]) && mailHops.testIP(received_ips[r],rline)){ - all_ips.unshift( received_ips[r] ); - } - } - //reset the line - rline=''; - } - } - - // parse dates - if(firstDate && firstDate.indexOf('(') !==- 1) - firstDate = firstDate.substring(0,firstDate.indexOf('(')).trim(); - if(lastDate && lastDate.indexOf('(') !== -1) - lastDate = lastDate.substring(0,lastDate.indexOf('(')).trim(); - if(firstDate && lastDate){ - try { - firstDate = new Date(firstDate); - lastDate = new Date(lastDate); - mailHops.message.time = lastDate - firstDate; - } catch(e){ - mailHops.LOG('travel dates parse Error: '+JSON.stringify(e)); - mailHops.message.time = null; - } - } else { - mailHops.message.time = null; - } - - //get the originating IP address - if(!!headXOrigIP){ - headXOrigIP = headXOrigIP.replace(/\[IPv6\:/g,'['); - //IPV6 check - if(headXOrigIP.match(regexIPV6)){ - var ip = headXOrigIP.match(regexIPV6) - if(!!ip && ip.length && all_ips.indexOf(ip[0])==-1) - all_ips.unshift( ip[0] ); - } else { - var ip = headXOrigIP.match(regexAllIp); - if(!!ip && ip.length && all_ips.indexOf(ip[0])==-1) - all_ips.unshift( ip[0] ); - } - } - - if ( all_ips.length ){ - mailHops.lookupRoute ( all_ips ) ; - } else { - mailHopsDisplay.clear( true ); - } -}; -//another ip check, dates will throw off the regex -mailHops.testIP = function(ip,header){ - var validIP = true; - - try { - var firstchar = header.substring(header.indexOf(ip)-1); - firstchar = firstchar.substring(0,1); - var lastchar = header.substring((header.indexOf(ip)+ip.length)); - lastchar = lastchar.substring(0,1); - - if(firstchar.match(/\.|\d|\-/) - || lastchar.match(/\.|\d|\-/) - || ( firstchar == '?' && lastchar == '?' ) - || (firstchar == ':' || lastchar == ':') - || lastchar == ';' - || header.toLowerCase().indexOf(' id '+ip) !== -1 - || parseInt(ip.substring(0,ip.indexOf('.'))) >= 240 //IANA-RESERVED - ){ - //only if there is one instance of this IP - if(header.indexOf(ip) == header.lastIndexOf(ip)) - validIP = false; - } else if(header.indexOf('using SSL') !== -1 - || header.indexOf('using TLS') !== -1 - || header.indexOf('version=TLSv1/SSLv3') !== -1 - ){ - //check if this IP was part of a secure transmission - mailHops.message.secure.push(ip); - } - } catch(e) { - mailHops.LOG('testIP Error: '+JSON.stringify(e)); - } - return validIP; -}; - -mailHops.setupEventListener = function () { - if ( mailHops.isLoaded ){ - return; - } - mailHops.LOG("Setting up Message listener"); - - mailHops.init(); - mailHops.registerObserver(); - - var listener = { - onStartHeaders: function() { mailHopsDisplay.clear(); } - , onEndHeaders: mailHops.loadHeaderData - }; - gMessageListeners.push( listener ); -}; - -//preferences observers -mailHops.registerObserver = function(){ - var prefService = Components.classes["@mozilla.org/preferences-service;1"].getService ( Ci.nsIPrefService ) ; - mailHops._branch = prefService.getBranch("mail.mailHops."); - if (!("addObserver" in mailHops._branch)) - mailHops._branch.QueryInterface(Components.interfaces.nsIPrefBranch2); - - mailHops._branch.addObserver( "" , mailHops , false ) ; -}; - -mailHops.unregisterObserver = function(){ - if ( !mailHops._branch ){ - return ; - } - - mailHops._branch.removeObserver ( "" , mailHops ) ; -}; - -mailHops.observe = function ( aSubject , aTopic , aData ) -{ - if ( aTopic == "nsPref:changed" ) - mailHops.loadPref(true); -}; - -mailHops.getCharPref = function ( strName , strDefault ){ - var value; - if (!pref){ - var pref = Components.classes["@mozilla.org/preferences-service;1"].getService( Ci.nsIPrefBranch ) ; - } - try { - value = pref.getCharPref ( strName ) ; - } catch(e){ - value = strDefault ; - } - return ( value ) ; -}; - -//mailhops lookup -mailHops.lookupRoute = function(header_route){ - - //setup loading - mailHopsDisplay.clear(); - - var lookupURL = mailHopsUtils.getAPIUrl(mailHops.options)+'/lookup/?'+mailHopsUtils.getAPIUrlParams(mailHops.options)+'&r='+String(header_route)+'&l='+mailHops.options.lan+'&u='+mailHops.options.unit; - - if(mailHops.options.fkey != '') - lookupURL += '&fkey='+mailHops.options.fkey; - if(mailHops.message.time != null) - lookupURL += '&t='+mailHops.message.time; - - //check for cache - var cached_results = mailHops.getResults(); - - if(cached_results){ - mailHops.LOG('Found Cached Result'); - try { - cached_results = JSON.parse(cached_results); - mailHopsDisplay.route(header_route, mailHops.message, cached_results.response, cached_results.meta, lookupURL); - return; - } catch(e){ - mailHops.LOG('Failed to parse cached result: '+JSON.stringify(e)); - } - } - -mailHops.LOG(lookupURL); - - //call mailhops api for lookup - var xmlhttp = new XMLHttpRequest(); - - xmlhttp.open("GET", lookupURL ,true); - xmlhttp.onreadystatechange=function() { - if (xmlhttp.readyState===4){ - try { - var data = JSON.parse(xmlhttp.responseText); - if(xmlhttp.status===200){ - var d = new Date(); - data.meta.cached = d.toISOString(); - //save the result - mailHops.saveResults(data, data.response.route); - //display the result - mailHopsDisplay.route(header_route, mailHops.message, data.response, data.meta, lookupURL); - } else if(data.error){ - mailHops.LOG(JSON.stringify(data)); - //display the error - mailHopsDisplay.error(xmlhttp.status,data); - } - } catch(e){ - mailHops.LOG(e); - mailHopsDisplay.error(); - } - } - }; - xmlhttp.send(null); -}; - -mailHops.saveResults = function(results, route){ - - if(!mailHops.msgURI) - return false; - - var messenger = Components.classes["@mozilla.org/messenger;1"].createInstance().QueryInterface(Components.interfaces.nsIMessenger); - var msgHdr = messenger.messageServiceFromURI(mailHops.msgURI).messageURIToMsgHdr(mailHops.msgURI); - - if(!msgHdr) - return false; - - if(!results){ - msgHdr.setStringProperty( "MH-Route", '' ); - return false; - } - - var countryCode = mailHopsUtils.getOriginatingCountryCode(route); - - if(!!countryCode){ - results.sender = { countryCode: countryCode }; - } - - msgHdr.setStringProperty( "MH-Route", JSON.stringify(results) ); - - //Add tag - if(!!countryCode && !!mailHops.options.api_key){ - try { - var msg = Components.classes["@mozilla.org/array;1"].createInstance(Components.interfaces.nsIMutableArray); - msg.clear(); - msg.appendElement(msgHdr, false); - - if(!!mailHops.options.country_tag){ - var tagService = Components.classes["@mozilla.org/messenger/tagservice;1"].getService(Components.interfaces.nsIMsgTagService); - if(!tagService) - return; - - if(!tagService.getKeyForTag(countryCode)) - tagService.addTag(countryCode,'',0); - - msgHdr.folder.addKeywordsToMessages(msg, countryCode ); - mailHops.LOG( "Added CountryCode tag: "+countryCode ); - } - - if(!!mailHops.options.country_filter && mailHops.options.country_filter.length){ - if(mailHops.options.country_filter.indexOf(countryCode.toLowerCase()) !== -1){ - msgHdr.folder.setJunkScoreForMessages(msg, "100"); - mailHops.LOG( "Junk: Country Filter match" ); - } - } - // tag as junk if travel time is longer than 10 seconds - if(!!mailHops.options.travel_time_junk && mailHops.message.time != null && mailHops.message.time > 10000){ - msgHdr.folder.setJunkScoreForMessages(msg, "100"); - mailHops.LOG( "Junk: Travel time match" ); - } - - } catch(e){ - mailHops.LOG( "Error adding CountryCode tag: "+e ); - } - } -}; - -mailHops.getResults = function(){ - - if(!mailHops.msgURI) - return false; - - var messenger = Components.classes["@mozilla.org/messenger;1"].createInstance().QueryInterface(Components.interfaces.nsIMessenger); - var msgHdr = messenger.messageServiceFromURI(mailHops.msgURI).messageURIToMsgHdr(mailHops.msgURI); - - if(!msgHdr) - return false; - - return msgHdr.getStringProperty( "MH-Route" ); -}; - -mailHops.refreshCache = function(){ - mailHops.saveResults(); - mailHops.getRoute(); -}; - -// window.addEventListener("messagepane-loaded", mailHops.setupEventListener, true); -window.addEventListener("load", function() { - var messagepane = document.getElementById("messagepane"); - if (messagepane) { - messagepane.addEventListener("load", function () { - mailHops.setupEventListener(); - }, true); - } -}, false); \ No newline at end of file diff --git a/chrome/content/mailhops-4-preferences.js b/chrome/content/mailhops-4-preferences.js deleted file mode 100644 index 5a34234..0000000 --- a/chrome/content/mailhops-4-preferences.js +++ /dev/null @@ -1,272 +0,0 @@ -if (!pref) { - var pref = Components.classes["@mozilla.org/preferences-service;1"].getService ( Ci.nsIPrefBranch ) ; -} - -var mailHopPreferences = { - api_host: 'api.mailhops.com', //mailhops api url - api_http: 'https://', //ssl? - api_key: '', //api key - valid_api_key: false, - fkey: '', //forecast.io api key - country_filter: [], - previewBar: null, - - loadPreferences: function(){ - var self = this; - - this.api_host = document.getElementById("mailhop.api_host"); - - this.api_http = document.getElementById("mailhop.api_http"); - - this.api_key = document.getElementById("mailhop.api_key"); - - this.fkey = document.getElementById("mailhop.fkey"); - - this.previewBar = document.getElementById("display_preview"); - - document.getElementById("mailhop.lang").value = pref.getCharPref("mail.mailHops.lang",'en'); - - document.getElementById("mailhop.map_provider").value = pref.getCharPref("mail.mailHops.map_provider",'OpenStreetMap.Mapnik'); - - if(pref.getCharPref("mail.mailHops.unit",'mi')=='mi') - document.getElementById("mailhop.unit").selectedIndex = 0; - else - document.getElementById("mailhop.unit").selectedIndex = 1; - - //Display Box styles - document.getElementById("mailhop.bar_color").value = pref.getCharPref("mail.mailHops.bar_color",'#FFF'); - document.getElementById("mailhop.font_color").value = pref.getCharPref("mail.mailHops.font_color",'#777'); - document.getElementById("mailhop.font_size").value = pref.getCharPref("mail.mailHops.font_size",'14px'); - - //Update styles - this.previewBar.style.background = document.getElementById("mailhop.bar_color").value; - this.previewBar.style.color = document.getElementById("mailhop.font_color").value; - this.previewBar.style.fontSize = document.getElementById("mailhop.font_size").value; - - if(pref.getCharPref("mail.mailHops.debug",'true')=='true') - document.getElementById("mailhop.debug").checked = true; - else - document.getElementById("mailhop.debug").checked = false; - - // API info - this.api_key.value = pref.getCharPref("mail.mailHops.api_key",''); - - this.api_http.value = pref.getCharPref("mail.mailHops.api_http",'https://'); - if(this.api_http.value=='https://') - this.api_http.selectedIndex = 0; - else - this.api_http.selectedIndex = 1; - - this.api_host.value = pref.getCharPref("mail.mailHops.api_host",'api.mailhops.com'); - - this.fkey.value = pref.getCharPref("mail.mailHops.fkey",''); - - // Country Filter and tagging - this.country_filter = JSON.parse(pref.getCharPref("mail.mailHops.country_filter",null) || []); - if(this.country_filter.length){ - for(c in this.country_filter){ - document.getElementById("country_"+this.country_filter[c]).checked=true; - } - } - if(!!this.api_key.value.trim()){ - document.getElementById("mailhops-membership-link").value='My Account'; - document.getElementById("mailhops-membership-link").setAttribute('href','https://mailhops.com/account/'+this.api_key.value.trim()); - } - if(pref.getCharPref("mail.mailHops.country_tag",'false')=='false') - document.getElementById("mailhop.country_tag").checked = false; - else - document.getElementById("mailhop.country_tag").checked = true; - - if(pref.getCharPref("mail.mailHops.travel_time_junk",'false')=='false') - document.getElementById("mailhop.travel_time_junk").checked = false; - else - document.getElementById("mailhop.travel_time_junk").checked = true; - - if(pref.getCharPref("mail.mailHops.hide_compact",'false')=='false') - document.getElementById("mailhop.hide_compact").checked = false; - else - document.getElementById("mailhop.hide_compact").checked = true; - - this.saveAPIKey(); - - document.getElementById("mailhop.bar_color").addEventListener("input", function () { - self.previewBar.style.background = this.value; - }); - document.getElementById("mailhop.font_color").addEventListener("input", function () { - self.previewBar.style.color = this.value; - }); - document.getElementById("mailhop.font_size").addEventListener("input", function () { - self.previewBar.style.fontSize = this.value; - }); - document.addEventListener("dialogaccept", function(event) { - mailHopPreferences.savePreferences(); - }); - }, - savePreferences: function() { - pref.setCharPref("mail.mailHops.lang", document.getElementById("mailhop.lang").selectedItem.value); - pref.setCharPref("mail.mailHops.map_provider", document.getElementById("mailhop.map_provider").selectedItem.value); - pref.setCharPref("mail.mailHops.unit", document.getElementById("mailhop.unit").selectedItem.value); - pref.setCharPref("mail.mailHops.bar_color", String(document.getElementById("mailhop.bar_color").value)); - pref.setCharPref("mail.mailHops.font_color", String(document.getElementById("mailhop.font_color").value)); - pref.setCharPref("mail.mailHops.font_size", String(document.getElementById("mailhop.font_size").value)); - pref.setCharPref("mail.mailHops.debug", String(document.getElementById("mailhop.debug").checked)); - pref.setCharPref("mail.mailHops.hide_compact", String(document.getElementById("mailhop.hide_compact").checked)); - - //API vars - if(!this.valid_api_key) - this.api_key.value=''; - pref.setCharPref("mail.mailHops.api_key", this.api_key.value.trim()); - pref.setCharPref("mail.mailHops.api_http", this.api_http.value); - pref.setCharPref("mail.mailHops.api_host", this.api_host.value); - - pref.setCharPref("mail.mailHops.fkey", String(this.fkey.value)); - - // Country Filter and tagging - this.country_filter = []; - for(c in mailHopsUtils.countries){ - if(document.getElementById("country_"+mailHopsUtils.countries[c]).checked) - this.country_filter.push(document.getElementById("country_"+mailHopsUtils.countries[c]).getAttribute('value')); - } - pref.setCharPref("mail.mailHops.country_filter", String(JSON.stringify(this.country_filter))); - pref.setCharPref("mail.mailHops.country_tag", String(document.getElementById("mailhop.country_tag").checked)); - pref.setCharPref("mail.mailHops.travel_time_junk", String(document.getElementById("mailhop.travel_time_junk").checked)); - - return true; - }, - - countryListSelectAll: function(all){ - if(this.valid_api_key){ - for(c in mailHopsUtils.countries){ - document.getElementById("country_"+mailHopsUtils.countries[c]).checked=all; - } - } - }, - planError: function(error){ - this.valid_api_key=false; - document.getElementById("plan-error").style.display = 'block'; - document.getElementById("plan-error").value=error; - document.getElementById("plan").value=''; - document.getElementById("status").value=''; - document.getElementById("rate-limit").value=''; - document.getElementById("rate-remaining").value=''; - document.getElementById("rate-reset").value=''; - document.getElementById("mailhops-membership-link").value='Join MailHops'; - document.getElementById("mailhops-membership-link").setAttribute('href','https://mailhops.com'); - var items = document.getElementsByClassName('filters'); - for(x in items){ - items[x].disabled = true; - } - var items = document.getElementsByClassName('country'); - for(x in items){ - items[x].disabled = true; - if(items[x].label) - items[x].label = items[x].label.toUpperCase(); - } - }, - saveAPIKey: function() { - - if(!!this.api_key && this.api_key.value != ''){ - var xmlhttp = new XMLHttpRequest(); - var apiBase = this.api_http.value+this.api_host.value, - accountURL = '/v2/accounts/?api_key='+this.api_key.value.trim(), - api_key = this.api_key.value.trim(), - self = this; - - xmlhttp.open("GET", apiBase+accountURL, true); - xmlhttp.onreadystatechange=function() { - if (xmlhttp.readyState===4) { - try { - var data = JSON.parse(xmlhttp.responseText); - if(xmlhttp.status===200){ - self.valid_api_key=true; - document.getElementById("plan-error").style.display = 'none'; - // set plan info - document.getElementById("plan").value = "Plan: "+data.account.subscriptions.data[0].plan.name; - document.getElementById("status").value = "Status: "+data.account.subscriptions.data[0].status; - document.getElementById("rate-limit").value = "Limit: "+data.account.rate.limit; - document.getElementById("rate-remaining").value = "Remaining: "+data.account.rate.remaining; - if(data.account.rate.reset/60 < 60) - document.getElementById("rate-reset").value = "Resets in: "+Math.round(data.account.rate.reset/60)+" min."; - else - document.getElementById("rate-reset").value = "Resets in: "+Math.round(data.account.rate.reset/60/60)+" hr."; - document.getElementById("mailhops-membership-link").value='My Account'; - document.getElementById("mailhops-membership-link").setAttribute('href','https://mailhops.com/account/'+api_key); - - var items = document.getElementsByClassName('filters'); - for(x in items){ items[x].disabled = false;} - var items = document.getElementsByClassName('country'); - for(x in items){ items[x].disabled = false; if(items[x].label) items[x].label = items[x].label.toUpperCase();} - } else if(!!data.error){ - self.planError(xmlhttp.status+': '+data.error.message); - } - mailHopPreferences.savePreferences(); - } catch (e){ - self.planError('Connection Failed to\n '+e+'!'); - } - } - }; - xmlhttp.send(null); - } else { - this.planError('Enter a valid API key above.'); - } - }, - - TestConnection: function(){ - var xmlhttp = new XMLHttpRequest(); - var apiBase = this.api_http.value+this.api_host.value, - lookupURL = '/v1/lookup/?healthcheck'; - - xmlhttp.open("GET", apiBase+lookupURL,true); - xmlhttp.onreadystatechange=function() { - if (xmlhttp.readyState===4) { - try{ - var data = JSON.parse(xmlhttp.responseText); - if(xmlhttp.status===200){ - alert('Connection Succeeded to\n '+apiBase+'!'); - } else { - //display the error - alert('Connection Failed to\n '+apiBase+'!'); - } - } - catch (ex){ - alert('Connection Failed to\n '+apiBase+'! '+JSON.stringify(ex)); - } - } - }; - xmlhttp.send(null); -}, - - ResetConnection: function(){ - this.api_http.value=="https://"; - this.api_http.selectedIndex = 0; - this.api_host.value='api.mailhops.com'; - }, - - ResetDisplay: function(bar,font,size){ - if(bar){ - if(bar.indexOf('rgb(')===0) - document.getElementById("mailhop.bar_color").value = this.rgb2hex(bar); - else - document.getElementById("mailhop.bar_color").value = bar; - } - if(font) { - if(font.indexOf('rgb(')===0) - document.getElementById("mailhop.font_color").value = this.rgb2hex(font); - else - document.getElementById("mailhop.font_color").value = font; - } - if(size) document.getElementById("mailhop.font_size").value = size; - this.previewBar.style.background = document.getElementById("mailhop.bar_color").value; - this.previewBar.style.color = document.getElementById("mailhop.font_color").value; - this.previewBar.style.fontSize = document.getElementById("mailhop.font_size").value; - }, - - rgb2hex: function(rgb) { - rgb = rgb.match(/^rgb\((\d+),\s*(\d+),\s*(\d+)\)$/); - function hex(x) { - return ("0" + parseInt(x).toString(16)).slice(-2); - } - return "#" + hex(rgb[1]) + hex(rgb[2]) + hex(rgb[3]); - } - - }; diff --git a/chrome/content/mailhops-5-msgListColumn.js b/chrome/content/mailhops-5-msgListColumn.js deleted file mode 100644 index 8cace5e..0000000 --- a/chrome/content/mailhops-5-msgListColumn.js +++ /dev/null @@ -1,75 +0,0 @@ -var columnHandler = { - getCellText: function(row, col) {return null;}, - getSortStringForRow: function(msgHdr) { - msgHdr.getStringProperty( "MH-Route" ); - var countryCode = null; - var cached_results = msgHdr.getStringProperty( "MH-Route" ); - if(cached_results){ - try { - cached_results = JSON.parse(cached_results); - if(cached_results.sender && cached_results.sender.countryCode){ - countryCode = cached_results.sender.countryCode; - } else { - countryCode = mailHopsUtils.getOriginatingCountryCode(cached_results.response.route); - } - if(countryCode){ - return 'chrome://mailhops/content/images/flags/'+countryCode.toLowerCase()+'.png'; - } - } catch(e) { - return countryCode; - } - } - return countryCode; - }, - isString: function() {return true;}, - - getCellProperties: function (row, col, props) { - return 'colMailHops'; - }, - getRowProperties: function(row, props){}, - getImageSrc: function (row, col) { - var msgKey = gDBView.getKeyAt(row); - var msgHdr = gDBView.db.GetMsgHdrForKey(msgKey); - var countryCode = null; - var cached_results = msgHdr.getStringProperty( "MH-Route" ); - if(cached_results){ - try { - cached_results = JSON.parse(cached_results); - if(cached_results.sender && cached_results.sender.countryCode){ - countryCode = cached_results.sender.countryCode; - } else { - countryCode = mailHopsUtils.getOriginatingCountryCode(cached_results.response.route); - } - if(countryCode){ - return 'chrome://mailhops/content/images/flags/'+countryCode.toLowerCase()+'.png'; - } - } catch(e) { - return null; - } - } - return null; - }, - getSortLongForRow: function(hdr) {return 0;} - }; - -var CreateDbObserver = { - // Components.interfaces.nsIObserver - observe: function(aMsgFolder, aTopic, aData) - { - addCustomColumnHandler(); - } -}; - -function doOnceLoaded() { - var ObserverService = Components.classes["@mozilla.org/observer-service;1"].getService(Components.interfaces.nsIObserverService); - ObserverService.addObserver(CreateDbObserver, "MsgCreateDBView", false); -} - -function addCustomColumnHandler() { - gDBView.addColumnHandler("colMailHops", columnHandler); - if ("COLUMNS_MAP_NOSORT" in gFolderDisplay) { - gFolderDisplay.COLUMNS_MAP_NOSORT.add("colMailHops"); - } -} - -window.addEventListener("load", doOnceLoaded, false); \ No newline at end of file diff --git a/chrome/content/mailhopsMap.xul b/chrome/content/mailhopsMap.xul deleted file mode 100644 index 708b33f..0000000 --- a/chrome/content/mailhopsMap.xul +++ /dev/null @@ -1,22 +0,0 @@ - - - - - - - - - - - - diff --git a/chrome/content/msgListColumn.xul b/chrome/content/msgListColumn.xul deleted file mode 100644 index 29470f5..0000000 --- a/chrome/content/msgListColumn.xul +++ /dev/null @@ -1,15 +0,0 @@ - - - - - - - - - - - - \ No newline at end of file diff --git a/chrome/content/msgNotificationBar.xul b/chrome/content/msgNotificationBar.xul deleted file mode 100644 index cdb20a3..0000000 --- a/chrome/content/msgNotificationBar.xul +++ /dev/null @@ -1,55 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/chrome/content/preferences.xul b/chrome/content/preferences.xul deleted file mode 100644 index bfa2778..0000000 --- a/chrome/content/preferences.xul +++ /dev/null @@ -1,617 +0,0 @@ - - - - - - -%MailHopsDTD; -]> - - - - - - - - - - - - - - - - - - - - - - API Key - - - - Save API Key - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Mark messages as Junk from Countries checked below. - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Use any . - - - - - MailHops Bar - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Reset Display - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - &mailhops_connection_test; - &mailhops_connection_reset; - - - - - - - - - MailHops API uses to get the weather of the sender, register for an API Key to enable this feature. - - - - - - - - - - - - - diff --git a/chrome/locale/de/prefs.dtd b/chrome/locale/de/prefs.dtd deleted file mode 100644 index 246dc99..0000000 --- a/chrome/locale/de/prefs.dtd +++ /dev/null @@ -1,8 +0,0 @@ - - - - - - - - diff --git a/chrome/locale/de/strings.dtd b/chrome/locale/de/strings.dtd deleted file mode 100644 index e808497..0000000 --- a/chrome/locale/de/strings.dtd +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - - - - diff --git a/chrome/locale/en/prefs.dtd b/chrome/locale/en/prefs.dtd deleted file mode 100644 index 00e7e42..0000000 --- a/chrome/locale/en/prefs.dtd +++ /dev/null @@ -1,8 +0,0 @@ - - - - - - - - diff --git a/chrome/locale/en/strings.dtd b/chrome/locale/en/strings.dtd deleted file mode 100644 index ffb003c..0000000 --- a/chrome/locale/en/strings.dtd +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - - - - diff --git a/chrome/locale/es/prefs.dtd b/chrome/locale/es/prefs.dtd deleted file mode 100644 index 7a8d1b9..0000000 --- a/chrome/locale/es/prefs.dtd +++ /dev/null @@ -1,8 +0,0 @@ - - - - - - - - diff --git a/chrome/locale/es/strings.dtd b/chrome/locale/es/strings.dtd deleted file mode 100644 index d8d2c35..0000000 --- a/chrome/locale/es/strings.dtd +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - - - - diff --git a/chrome/locale/fr/prefs.dtd b/chrome/locale/fr/prefs.dtd deleted file mode 100644 index 033b2b2..0000000 --- a/chrome/locale/fr/prefs.dtd +++ /dev/null @@ -1,8 +0,0 @@ - - - - - - - - diff --git a/chrome/locale/fr/strings.dtd b/chrome/locale/fr/strings.dtd deleted file mode 100644 index b2eea51..0000000 --- a/chrome/locale/fr/strings.dtd +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - - - - diff --git a/chrome/locale/ja/prefs.dtd b/chrome/locale/ja/prefs.dtd deleted file mode 100644 index d1feea4..0000000 --- a/chrome/locale/ja/prefs.dtd +++ /dev/null @@ -1,8 +0,0 @@ - - - - - - - - diff --git a/chrome/locale/ja/strings.dtd b/chrome/locale/ja/strings.dtd deleted file mode 100644 index c130b6d..0000000 --- a/chrome/locale/ja/strings.dtd +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - - - - diff --git a/chrome/locale/pl/prefs.dtd b/chrome/locale/pl/prefs.dtd deleted file mode 100644 index fbdbfac..0000000 --- a/chrome/locale/pl/prefs.dtd +++ /dev/null @@ -1,8 +0,0 @@ - - - - - - - - diff --git a/chrome/locale/pl/strings.dtd b/chrome/locale/pl/strings.dtd deleted file mode 100644 index ee2295a..0000000 --- a/chrome/locale/pl/strings.dtd +++ /dev/null @@ -1,10 +0,0 @@ - - - - - - - - - - diff --git a/chrome/locale/pt-BR/prefs.dtd b/chrome/locale/pt-BR/prefs.dtd deleted file mode 100644 index 289f30e..0000000 --- a/chrome/locale/pt-BR/prefs.dtd +++ /dev/null @@ -1,8 +0,0 @@ - - - - - - - - diff --git a/chrome/locale/pt-BR/strings.dtd b/chrome/locale/pt-BR/strings.dtd deleted file mode 100644 index 57fa712..0000000 --- a/chrome/locale/pt-BR/strings.dtd +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - - - - diff --git a/chrome/locale/ru/prefs.dtd b/chrome/locale/ru/prefs.dtd deleted file mode 100644 index 3d72d34..0000000 --- a/chrome/locale/ru/prefs.dtd +++ /dev/null @@ -1,8 +0,0 @@ - - - - - - - - diff --git a/chrome/locale/ru/strings.dtd b/chrome/locale/ru/strings.dtd deleted file mode 100644 index d942635..0000000 --- a/chrome/locale/ru/strings.dtd +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - - - - diff --git a/chrome/locale/zh-CN/prefs.dtd b/chrome/locale/zh-CN/prefs.dtd deleted file mode 100644 index 263e744..0000000 --- a/chrome/locale/zh-CN/prefs.dtd +++ /dev/null @@ -1,8 +0,0 @@ - - - - - - - - diff --git a/chrome/locale/zh-CN/strings.dtd b/chrome/locale/zh-CN/strings.dtd deleted file mode 100644 index 4dd569b..0000000 --- a/chrome/locale/zh-CN/strings.dtd +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - - - - diff --git a/chrome/skin/classic/msgNotificationBar.css b/chrome/skin/classic/msgNotificationBar.css deleted file mode 100644 index 1caf87b..0000000 --- a/chrome/skin/classic/msgNotificationBar.css +++ /dev/null @@ -1,161 +0,0 @@ -@namespace url("http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"); - -#mailhopsResultText { padding-left:20px; background-repeat: no-repeat; } - -#mailhopsNoficationBox menuitem .menu-iconic-icon { width: 16px; height: 11px; } - -#mailhopsNoficationBox .auth-item { display: none; background-repeat: no-repeat; padding-left: 18px; } - -#mhTabs .act { padding-left: 20px; background-repeat: no-repeat; outline : none;} - -#mailhopsResultWeather { display: none; background-repeat: no-repeat; padding-left: 18px; } - -#mailHopsPreferences { - font-family: 'Raleway',Arial,sans-serif; - font-size: 14px; -} - -#mailHopsPreferences textbox { - font-size: 14px; - padding: 5px; - color: #777; -} - -#mailHopsPreferences tab { - font-size: 14px; - padding: 5px; - color: #333; -} - -#mailhopsResult label { - margin-top: 8px; -} - -#mailhopsNoficationBox { - font-family: "Helvetica Neue",Helvetica,Arial,sans-serif; - font-size: 14px; - line-height: 24px; - font-weight: normal; - position: relative; - max-height: 50px; - width: 100%; - margin: auto; -} - -#mailhopsNotification { - background: #f7f7f7; -} - -#mailhopsResult { - position: relative; - display: inline-flex; -} - -#mailhopsNoficationBox .bar-link { - cursor: pointer; - text-decoration: none; -} - -#mailhopsNoficationBox .bar-link:hover { - text-decoration: underline; -} - -#mailhopsNoficationBox #mailhopsDataPanePrefsLink { - border-radius: 20px; - background-color: #CCC; - letter-spacing: .1em; - right: 0; -} - -#mailhopsLogo, -#mailhopsResultText, -#mailhopsResultWeather, -#mailhopsUnsubscribe, -#mailhopsDataPaneDNSBL, -#mailhopsDataPaneDKIM, -#mailhopsDataPaneSPF, -#mailhopsDataPaneMailer { - color: #fff; -} - -#mailhopsLogo, -#mailhopsResultText, -#mailhopsResultWeather, -#mailhopsUnsubscribe { - cursor: pointer; -} - -#mailhopsNoficationBox .unsubscribe { - color: #CCC; -} - -#mailhopsLogo { - -webkit-filter: grayscale(100%); - filter: grayscale(100%); -} - -#mailhopsLogo:hover { - -webkit-filter: none; - filter: none; -} - -#mailHopsAccountMessage { - display: none; -} - -#mailhopsDataPaneDetails { - border-radius: 10px; - display: none; - padding: 10px; - border: 1px solid #CCC; - color: #333; - background-color: #FFF; - position: fixed; - margin-top: 0; - z-index: 10000; -} - -#mailhopsDataPaneDetails .hop { - background-repeat: no-repeat; - display: block; - position: relative; - padding-left: 22px; -} - -#mailhopsDataPaneDetails .host { - background-repeat: no-repeat; - display: block; - position: relative; - color: #777; - padding-left: 22px; - margin-left: 22px; -} - -#mailhopsNoficationBox toolbarseparator { - appearance: none; - -moz-appearance: none; - margin: 3px 0px 3px 0px!important; -} - -#mailhopsNoficationBox .toolbarbutton { - font-family: Lato,'Helvetica Neue',Arial,Helvetica,sans-serif; - font-weight: 400; - padding: 0 4px 0 4px; - margin: unset!important; - color: #777!important; - cursor: pointer; -} - -#mailhopsNoficationBox #mailhopsHopsBox:hover, -#mailhopsNoficationBox #mailhopsRefreshBox:hover, -#mailhopsNoficationBox #mailhopsUnsubscribeBox:hover, -#mailhopsNoficationBox #mailhopsHopsBox.active { - color: #333; - background-color: #e5e5e5; - border-radius: 10px; -} - -#mailhopsNoficationBox .messageCloseButton, -#mailhopsNoficationBox .messageDetails:nth-child(2) { - display: none!important; -} \ No newline at end of file diff --git a/chrome/skin/classic/prefs.css b/chrome/skin/classic/prefs.css deleted file mode 100644 index 711513e..0000000 --- a/chrome/skin/classic/prefs.css +++ /dev/null @@ -1,25 +0,0 @@ -#mailHopsPreferences { - font-family: 'Raleway',Arial,sans-serif; - font-size: 14px; -} - -#mailHopsPreferences textbox { - font-size: 14px; - padding: 5px; - color: #777; -} - -#mailHopsPreferences tab { - font-size: 14px; - padding: 5px; - color: #333; -} - -#mailHopsPreferences button{ - height: 35px; - color: #333; -} - -#mailHopsPreferences .grid-color{ - margin-top: 7px; -} diff --git a/content/mailhops_details.xhtml b/content/mailhops_details.xhtml new file mode 100644 index 0000000..60ea737 --- /dev/null +++ b/content/mailhops_details.xhtml @@ -0,0 +1,24 @@ + + + + + + MailHops + + + + + + + + + + + Map + Options + + + + + + \ No newline at end of file diff --git a/content/preferences.html b/content/preferences.html new file mode 100644 index 0000000..c7bab5b --- /dev/null +++ b/content/preferences.html @@ -0,0 +1,43 @@ + + + + + + + + + + + + + + MailHops API Key + + + Join MailHops + + + OpenWeatherMap.org API Key + + + MailHops API uses OpenWeatherMap to get the weather of the sender + Register for an API Key to enable this feature. + + Save + + + MailHops Plan Info + + + + + + + + + + + + + + diff --git a/chrome/content/images/auth/bomb.png b/images/auth/bomb.png similarity index 100% rename from chrome/content/images/auth/bomb.png rename to images/auth/bomb.png diff --git a/chrome/content/images/auth/error.png b/images/auth/error.png similarity index 100% rename from chrome/content/images/auth/error.png rename to images/auth/error.png diff --git a/chrome/content/images/auth/fail.png b/images/auth/fail.png similarity index 100% rename from chrome/content/images/auth/fail.png rename to images/auth/fail.png diff --git a/chrome/content/images/auth/hardfail.png b/images/auth/hardfail.png similarity index 100% rename from chrome/content/images/auth/hardfail.png rename to images/auth/hardfail.png diff --git a/chrome/content/images/auth/lock.png b/images/auth/lock.png similarity index 100% rename from chrome/content/images/auth/lock.png rename to images/auth/lock.png diff --git a/chrome/content/images/auth/neutral.png b/images/auth/neutral.png similarity index 100% rename from chrome/content/images/auth/neutral.png rename to images/auth/neutral.png diff --git a/chrome/content/images/auth/none.png b/images/auth/none.png similarity index 100% rename from chrome/content/images/auth/none.png rename to images/auth/none.png diff --git a/chrome/content/images/auth/not_secure.png b/images/auth/not_secure.png similarity index 100% rename from chrome/content/images/auth/not_secure.png rename to images/auth/not_secure.png diff --git a/chrome/content/images/auth/pass.png b/images/auth/pass.png similarity index 100% rename from chrome/content/images/auth/pass.png rename to images/auth/pass.png diff --git a/chrome/content/images/auth/permerror.png b/images/auth/permerror.png similarity index 100% rename from chrome/content/images/auth/permerror.png rename to images/auth/permerror.png diff --git a/chrome/content/images/auth/secure.png b/images/auth/secure.png similarity index 100% rename from chrome/content/images/auth/secure.png rename to images/auth/secure.png diff --git a/chrome/content/images/auth/secure_host.png b/images/auth/secure_host.png similarity index 100% rename from chrome/content/images/auth/secure_host.png rename to images/auth/secure_host.png diff --git a/chrome/content/images/auth/softfail.png b/images/auth/softfail.png similarity index 100% rename from chrome/content/images/auth/softfail.png rename to images/auth/softfail.png diff --git a/chrome/content/images/auth/temperror.png b/images/auth/temperror.png similarity index 100% rename from chrome/content/images/auth/temperror.png rename to images/auth/temperror.png diff --git a/chrome/content/images/email.png b/images/email.png similarity index 100% rename from chrome/content/images/email.png rename to images/email.png diff --git a/chrome/content/images/flags/ad.png b/images/flags/ad.png similarity index 100% rename from chrome/content/images/flags/ad.png rename to images/flags/ad.png diff --git a/chrome/content/images/flags/ae.png b/images/flags/ae.png similarity index 100% rename from chrome/content/images/flags/ae.png rename to images/flags/ae.png diff --git a/chrome/content/images/flags/af.png b/images/flags/af.png similarity index 100% rename from chrome/content/images/flags/af.png rename to images/flags/af.png diff --git a/chrome/content/images/flags/ag.png b/images/flags/ag.png similarity index 100% rename from chrome/content/images/flags/ag.png rename to images/flags/ag.png diff --git a/chrome/content/images/flags/ai.png b/images/flags/ai.png similarity index 100% rename from chrome/content/images/flags/ai.png rename to images/flags/ai.png diff --git a/chrome/content/images/flags/al.png b/images/flags/al.png similarity index 100% rename from chrome/content/images/flags/al.png rename to images/flags/al.png diff --git a/chrome/content/images/flags/am.png b/images/flags/am.png similarity index 100% rename from chrome/content/images/flags/am.png rename to images/flags/am.png diff --git a/chrome/content/images/flags/an.png b/images/flags/an.png similarity index 100% rename from chrome/content/images/flags/an.png rename to images/flags/an.png diff --git a/chrome/content/images/flags/ao.png b/images/flags/ao.png similarity index 100% rename from chrome/content/images/flags/ao.png rename to images/flags/ao.png diff --git a/chrome/content/images/flags/ar.png b/images/flags/ar.png similarity index 100% rename from chrome/content/images/flags/ar.png rename to images/flags/ar.png diff --git a/chrome/content/images/flags/as.png b/images/flags/as.png similarity index 100% rename from chrome/content/images/flags/as.png rename to images/flags/as.png diff --git a/chrome/content/images/flags/at.png b/images/flags/at.png similarity index 100% rename from chrome/content/images/flags/at.png rename to images/flags/at.png diff --git a/chrome/content/images/flags/au.png b/images/flags/au.png similarity index 100% rename from chrome/content/images/flags/au.png rename to images/flags/au.png diff --git a/chrome/content/images/flags/aw.png b/images/flags/aw.png similarity index 100% rename from chrome/content/images/flags/aw.png rename to images/flags/aw.png diff --git a/chrome/content/images/flags/ax.png b/images/flags/ax.png similarity index 100% rename from chrome/content/images/flags/ax.png rename to images/flags/ax.png diff --git a/chrome/content/images/flags/az.png b/images/flags/az.png similarity index 100% rename from chrome/content/images/flags/az.png rename to images/flags/az.png diff --git a/chrome/content/images/flags/ba.png b/images/flags/ba.png similarity index 100% rename from chrome/content/images/flags/ba.png rename to images/flags/ba.png diff --git a/chrome/content/images/flags/bb.png b/images/flags/bb.png similarity index 100% rename from chrome/content/images/flags/bb.png rename to images/flags/bb.png diff --git a/chrome/content/images/flags/bd.png b/images/flags/bd.png similarity index 100% rename from chrome/content/images/flags/bd.png rename to images/flags/bd.png diff --git a/chrome/content/images/flags/be.png b/images/flags/be.png similarity index 100% rename from chrome/content/images/flags/be.png rename to images/flags/be.png diff --git a/chrome/content/images/flags/bf.png b/images/flags/bf.png similarity index 100% rename from chrome/content/images/flags/bf.png rename to images/flags/bf.png diff --git a/chrome/content/images/flags/bg.png b/images/flags/bg.png similarity index 100% rename from chrome/content/images/flags/bg.png rename to images/flags/bg.png diff --git a/chrome/content/images/flags/bh.png b/images/flags/bh.png similarity index 100% rename from chrome/content/images/flags/bh.png rename to images/flags/bh.png diff --git a/chrome/content/images/flags/bi.png b/images/flags/bi.png similarity index 100% rename from chrome/content/images/flags/bi.png rename to images/flags/bi.png diff --git a/chrome/content/images/flags/bj.png b/images/flags/bj.png similarity index 100% rename from chrome/content/images/flags/bj.png rename to images/flags/bj.png diff --git a/chrome/content/images/flags/bm.png b/images/flags/bm.png similarity index 100% rename from chrome/content/images/flags/bm.png rename to images/flags/bm.png diff --git a/chrome/content/images/flags/bn.png b/images/flags/bn.png similarity index 100% rename from chrome/content/images/flags/bn.png rename to images/flags/bn.png diff --git a/chrome/content/images/flags/bo.png b/images/flags/bo.png similarity index 100% rename from chrome/content/images/flags/bo.png rename to images/flags/bo.png diff --git a/chrome/content/images/flags/br.png b/images/flags/br.png similarity index 100% rename from chrome/content/images/flags/br.png rename to images/flags/br.png diff --git a/chrome/content/images/flags/bs.png b/images/flags/bs.png similarity index 100% rename from chrome/content/images/flags/bs.png rename to images/flags/bs.png diff --git a/chrome/content/images/flags/bt.png b/images/flags/bt.png similarity index 100% rename from chrome/content/images/flags/bt.png rename to images/flags/bt.png diff --git a/chrome/content/images/flags/bv.png b/images/flags/bv.png similarity index 100% rename from chrome/content/images/flags/bv.png rename to images/flags/bv.png diff --git a/chrome/content/images/flags/bw.png b/images/flags/bw.png similarity index 100% rename from chrome/content/images/flags/bw.png rename to images/flags/bw.png diff --git a/chrome/content/images/flags/by.png b/images/flags/by.png similarity index 100% rename from chrome/content/images/flags/by.png rename to images/flags/by.png diff --git a/chrome/content/images/flags/bz.png b/images/flags/bz.png similarity index 100% rename from chrome/content/images/flags/bz.png rename to images/flags/bz.png diff --git a/chrome/content/images/flags/ca.png b/images/flags/ca.png similarity index 100% rename from chrome/content/images/flags/ca.png rename to images/flags/ca.png diff --git a/chrome/content/images/flags/catalonia.png b/images/flags/catalonia.png similarity index 100% rename from chrome/content/images/flags/catalonia.png rename to images/flags/catalonia.png diff --git a/chrome/content/images/flags/cc.png b/images/flags/cc.png similarity index 100% rename from chrome/content/images/flags/cc.png rename to images/flags/cc.png diff --git a/chrome/content/images/flags/cd.png b/images/flags/cd.png similarity index 100% rename from chrome/content/images/flags/cd.png rename to images/flags/cd.png diff --git a/chrome/content/images/flags/cf.png b/images/flags/cf.png similarity index 100% rename from chrome/content/images/flags/cf.png rename to images/flags/cf.png diff --git a/chrome/content/images/flags/cg.png b/images/flags/cg.png similarity index 100% rename from chrome/content/images/flags/cg.png rename to images/flags/cg.png diff --git a/chrome/content/images/flags/ch.png b/images/flags/ch.png similarity index 100% rename from chrome/content/images/flags/ch.png rename to images/flags/ch.png diff --git a/chrome/content/images/flags/ci.png b/images/flags/ci.png similarity index 100% rename from chrome/content/images/flags/ci.png rename to images/flags/ci.png diff --git a/chrome/content/images/flags/ck.png b/images/flags/ck.png similarity index 100% rename from chrome/content/images/flags/ck.png rename to images/flags/ck.png diff --git a/chrome/content/images/flags/cl.png b/images/flags/cl.png similarity index 100% rename from chrome/content/images/flags/cl.png rename to images/flags/cl.png diff --git a/chrome/content/images/flags/cm.png b/images/flags/cm.png similarity index 100% rename from chrome/content/images/flags/cm.png rename to images/flags/cm.png diff --git a/chrome/content/images/flags/cn.png b/images/flags/cn.png similarity index 100% rename from chrome/content/images/flags/cn.png rename to images/flags/cn.png diff --git a/chrome/content/images/flags/co.png b/images/flags/co.png similarity index 100% rename from chrome/content/images/flags/co.png rename to images/flags/co.png diff --git a/chrome/content/images/flags/cr.png b/images/flags/cr.png similarity index 100% rename from chrome/content/images/flags/cr.png rename to images/flags/cr.png diff --git a/chrome/content/images/flags/cs.png b/images/flags/cs.png similarity index 100% rename from chrome/content/images/flags/cs.png rename to images/flags/cs.png diff --git a/chrome/content/images/flags/cu.png b/images/flags/cu.png similarity index 100% rename from chrome/content/images/flags/cu.png rename to images/flags/cu.png diff --git a/chrome/content/images/flags/cv.png b/images/flags/cv.png similarity index 100% rename from chrome/content/images/flags/cv.png rename to images/flags/cv.png diff --git a/chrome/content/images/flags/cx.png b/images/flags/cx.png similarity index 100% rename from chrome/content/images/flags/cx.png rename to images/flags/cx.png diff --git a/chrome/content/images/flags/cy.png b/images/flags/cy.png similarity index 100% rename from chrome/content/images/flags/cy.png rename to images/flags/cy.png diff --git a/chrome/content/images/flags/cz.png b/images/flags/cz.png similarity index 100% rename from chrome/content/images/flags/cz.png rename to images/flags/cz.png diff --git a/chrome/content/images/flags/de.png b/images/flags/de.png similarity index 100% rename from chrome/content/images/flags/de.png rename to images/flags/de.png diff --git a/chrome/content/images/flags/dj.png b/images/flags/dj.png similarity index 100% rename from chrome/content/images/flags/dj.png rename to images/flags/dj.png diff --git a/chrome/content/images/flags/dk.png b/images/flags/dk.png similarity index 100% rename from chrome/content/images/flags/dk.png rename to images/flags/dk.png diff --git a/chrome/content/images/flags/dm.png b/images/flags/dm.png similarity index 100% rename from chrome/content/images/flags/dm.png rename to images/flags/dm.png diff --git a/chrome/content/images/flags/do.png b/images/flags/do.png similarity index 100% rename from chrome/content/images/flags/do.png rename to images/flags/do.png diff --git a/chrome/content/images/flags/dz.png b/images/flags/dz.png similarity index 100% rename from chrome/content/images/flags/dz.png rename to images/flags/dz.png diff --git a/chrome/content/images/flags/ec.png b/images/flags/ec.png similarity index 100% rename from chrome/content/images/flags/ec.png rename to images/flags/ec.png diff --git a/chrome/content/images/flags/ee.png b/images/flags/ee.png similarity index 100% rename from chrome/content/images/flags/ee.png rename to images/flags/ee.png diff --git a/chrome/content/images/flags/eg.png b/images/flags/eg.png similarity index 100% rename from chrome/content/images/flags/eg.png rename to images/flags/eg.png diff --git a/chrome/content/images/flags/eh.png b/images/flags/eh.png similarity index 100% rename from chrome/content/images/flags/eh.png rename to images/flags/eh.png diff --git a/chrome/content/images/flags/england.png b/images/flags/england.png similarity index 100% rename from chrome/content/images/flags/england.png rename to images/flags/england.png diff --git a/chrome/content/images/flags/er.png b/images/flags/er.png similarity index 100% rename from chrome/content/images/flags/er.png rename to images/flags/er.png diff --git a/chrome/content/images/flags/es.png b/images/flags/es.png similarity index 100% rename from chrome/content/images/flags/es.png rename to images/flags/es.png diff --git a/chrome/content/images/flags/et.png b/images/flags/et.png similarity index 100% rename from chrome/content/images/flags/et.png rename to images/flags/et.png diff --git a/chrome/content/images/flags/europeanunion.png b/images/flags/europeanunion.png similarity index 100% rename from chrome/content/images/flags/europeanunion.png rename to images/flags/europeanunion.png diff --git a/chrome/content/images/flags/fam.png b/images/flags/fam.png similarity index 100% rename from chrome/content/images/flags/fam.png rename to images/flags/fam.png diff --git a/chrome/content/images/flags/fi.png b/images/flags/fi.png similarity index 100% rename from chrome/content/images/flags/fi.png rename to images/flags/fi.png diff --git a/chrome/content/images/flags/fj.png b/images/flags/fj.png similarity index 100% rename from chrome/content/images/flags/fj.png rename to images/flags/fj.png diff --git a/chrome/content/images/flags/fk.png b/images/flags/fk.png similarity index 100% rename from chrome/content/images/flags/fk.png rename to images/flags/fk.png diff --git a/chrome/content/images/flags/fm.png b/images/flags/fm.png similarity index 100% rename from chrome/content/images/flags/fm.png rename to images/flags/fm.png diff --git a/chrome/content/images/flags/fo.png b/images/flags/fo.png similarity index 100% rename from chrome/content/images/flags/fo.png rename to images/flags/fo.png diff --git a/chrome/content/images/flags/fr.png b/images/flags/fr.png similarity index 100% rename from chrome/content/images/flags/fr.png rename to images/flags/fr.png diff --git a/chrome/content/images/flags/ga.png b/images/flags/ga.png similarity index 100% rename from chrome/content/images/flags/ga.png rename to images/flags/ga.png diff --git a/chrome/content/images/flags/gb.png b/images/flags/gb.png similarity index 100% rename from chrome/content/images/flags/gb.png rename to images/flags/gb.png diff --git a/chrome/content/images/flags/gd.png b/images/flags/gd.png similarity index 100% rename from chrome/content/images/flags/gd.png rename to images/flags/gd.png diff --git a/chrome/content/images/flags/ge.png b/images/flags/ge.png similarity index 100% rename from chrome/content/images/flags/ge.png rename to images/flags/ge.png diff --git a/chrome/content/images/flags/gf.png b/images/flags/gf.png similarity index 100% rename from chrome/content/images/flags/gf.png rename to images/flags/gf.png diff --git a/chrome/content/images/flags/gh.png b/images/flags/gh.png similarity index 100% rename from chrome/content/images/flags/gh.png rename to images/flags/gh.png diff --git a/chrome/content/images/flags/gi.png b/images/flags/gi.png similarity index 100% rename from chrome/content/images/flags/gi.png rename to images/flags/gi.png diff --git a/chrome/content/images/flags/gl.png b/images/flags/gl.png similarity index 100% rename from chrome/content/images/flags/gl.png rename to images/flags/gl.png diff --git a/chrome/content/images/flags/gm.png b/images/flags/gm.png similarity index 100% rename from chrome/content/images/flags/gm.png rename to images/flags/gm.png diff --git a/chrome/content/images/flags/gn.png b/images/flags/gn.png similarity index 100% rename from chrome/content/images/flags/gn.png rename to images/flags/gn.png diff --git a/chrome/content/images/flags/gp.png b/images/flags/gp.png similarity index 100% rename from chrome/content/images/flags/gp.png rename to images/flags/gp.png diff --git a/chrome/content/images/flags/gq.png b/images/flags/gq.png similarity index 100% rename from chrome/content/images/flags/gq.png rename to images/flags/gq.png diff --git a/chrome/content/images/flags/gr.png b/images/flags/gr.png similarity index 100% rename from chrome/content/images/flags/gr.png rename to images/flags/gr.png diff --git a/chrome/content/images/flags/gs.png b/images/flags/gs.png similarity index 100% rename from chrome/content/images/flags/gs.png rename to images/flags/gs.png diff --git a/chrome/content/images/flags/gt.png b/images/flags/gt.png similarity index 100% rename from chrome/content/images/flags/gt.png rename to images/flags/gt.png diff --git a/chrome/content/images/flags/gu.png b/images/flags/gu.png similarity index 100% rename from chrome/content/images/flags/gu.png rename to images/flags/gu.png diff --git a/chrome/content/images/flags/gw.png b/images/flags/gw.png similarity index 100% rename from chrome/content/images/flags/gw.png rename to images/flags/gw.png diff --git a/chrome/content/images/flags/gy.png b/images/flags/gy.png similarity index 100% rename from chrome/content/images/flags/gy.png rename to images/flags/gy.png diff --git a/chrome/content/images/flags/hk.png b/images/flags/hk.png similarity index 100% rename from chrome/content/images/flags/hk.png rename to images/flags/hk.png diff --git a/chrome/content/images/flags/hm.png b/images/flags/hm.png similarity index 100% rename from chrome/content/images/flags/hm.png rename to images/flags/hm.png diff --git a/chrome/content/images/flags/hn.png b/images/flags/hn.png similarity index 100% rename from chrome/content/images/flags/hn.png rename to images/flags/hn.png diff --git a/chrome/content/images/flags/hr.png b/images/flags/hr.png similarity index 100% rename from chrome/content/images/flags/hr.png rename to images/flags/hr.png diff --git a/chrome/content/images/flags/ht.png b/images/flags/ht.png similarity index 100% rename from chrome/content/images/flags/ht.png rename to images/flags/ht.png diff --git a/chrome/content/images/flags/hu.png b/images/flags/hu.png similarity index 100% rename from chrome/content/images/flags/hu.png rename to images/flags/hu.png diff --git a/chrome/content/images/flags/id.png b/images/flags/id.png similarity index 100% rename from chrome/content/images/flags/id.png rename to images/flags/id.png diff --git a/chrome/content/images/flags/ie.png b/images/flags/ie.png similarity index 100% rename from chrome/content/images/flags/ie.png rename to images/flags/ie.png diff --git a/chrome/content/images/flags/il.png b/images/flags/il.png similarity index 100% rename from chrome/content/images/flags/il.png rename to images/flags/il.png diff --git a/chrome/content/images/flags/in.png b/images/flags/in.png similarity index 100% rename from chrome/content/images/flags/in.png rename to images/flags/in.png diff --git a/chrome/content/images/flags/io.png b/images/flags/io.png similarity index 100% rename from chrome/content/images/flags/io.png rename to images/flags/io.png diff --git a/chrome/content/images/flags/iq.png b/images/flags/iq.png similarity index 100% rename from chrome/content/images/flags/iq.png rename to images/flags/iq.png diff --git a/chrome/content/images/flags/ir.png b/images/flags/ir.png similarity index 100% rename from chrome/content/images/flags/ir.png rename to images/flags/ir.png diff --git a/chrome/content/images/flags/is.png b/images/flags/is.png similarity index 100% rename from chrome/content/images/flags/is.png rename to images/flags/is.png diff --git a/chrome/content/images/flags/it.png b/images/flags/it.png similarity index 100% rename from chrome/content/images/flags/it.png rename to images/flags/it.png diff --git a/chrome/content/images/flags/jm.png b/images/flags/jm.png similarity index 100% rename from chrome/content/images/flags/jm.png rename to images/flags/jm.png diff --git a/chrome/content/images/flags/jo.png b/images/flags/jo.png similarity index 100% rename from chrome/content/images/flags/jo.png rename to images/flags/jo.png diff --git a/chrome/content/images/flags/jp.png b/images/flags/jp.png similarity index 100% rename from chrome/content/images/flags/jp.png rename to images/flags/jp.png diff --git a/chrome/content/images/flags/ke.png b/images/flags/ke.png similarity index 100% rename from chrome/content/images/flags/ke.png rename to images/flags/ke.png diff --git a/chrome/content/images/flags/kg.png b/images/flags/kg.png similarity index 100% rename from chrome/content/images/flags/kg.png rename to images/flags/kg.png diff --git a/chrome/content/images/flags/kh.png b/images/flags/kh.png similarity index 100% rename from chrome/content/images/flags/kh.png rename to images/flags/kh.png diff --git a/chrome/content/images/flags/ki.png b/images/flags/ki.png similarity index 100% rename from chrome/content/images/flags/ki.png rename to images/flags/ki.png diff --git a/chrome/content/images/flags/km.png b/images/flags/km.png similarity index 100% rename from chrome/content/images/flags/km.png rename to images/flags/km.png diff --git a/chrome/content/images/flags/kn.png b/images/flags/kn.png similarity index 100% rename from chrome/content/images/flags/kn.png rename to images/flags/kn.png diff --git a/chrome/content/images/flags/kp.png b/images/flags/kp.png similarity index 100% rename from chrome/content/images/flags/kp.png rename to images/flags/kp.png diff --git a/chrome/content/images/flags/kr.png b/images/flags/kr.png similarity index 100% rename from chrome/content/images/flags/kr.png rename to images/flags/kr.png diff --git a/chrome/content/images/flags/kw.png b/images/flags/kw.png similarity index 100% rename from chrome/content/images/flags/kw.png rename to images/flags/kw.png diff --git a/chrome/content/images/flags/ky.png b/images/flags/ky.png similarity index 100% rename from chrome/content/images/flags/ky.png rename to images/flags/ky.png diff --git a/chrome/content/images/flags/kz.png b/images/flags/kz.png similarity index 100% rename from chrome/content/images/flags/kz.png rename to images/flags/kz.png diff --git a/chrome/content/images/flags/la.png b/images/flags/la.png similarity index 100% rename from chrome/content/images/flags/la.png rename to images/flags/la.png diff --git a/chrome/content/images/flags/lb.png b/images/flags/lb.png similarity index 100% rename from chrome/content/images/flags/lb.png rename to images/flags/lb.png diff --git a/chrome/content/images/flags/lc.png b/images/flags/lc.png similarity index 100% rename from chrome/content/images/flags/lc.png rename to images/flags/lc.png diff --git a/chrome/content/images/flags/li.png b/images/flags/li.png similarity index 100% rename from chrome/content/images/flags/li.png rename to images/flags/li.png diff --git a/chrome/content/images/flags/lk.png b/images/flags/lk.png similarity index 100% rename from chrome/content/images/flags/lk.png rename to images/flags/lk.png diff --git a/chrome/content/images/flags/lr.png b/images/flags/lr.png similarity index 100% rename from chrome/content/images/flags/lr.png rename to images/flags/lr.png diff --git a/chrome/content/images/flags/ls.png b/images/flags/ls.png similarity index 100% rename from chrome/content/images/flags/ls.png rename to images/flags/ls.png diff --git a/chrome/content/images/flags/lt.png b/images/flags/lt.png similarity index 100% rename from chrome/content/images/flags/lt.png rename to images/flags/lt.png diff --git a/chrome/content/images/flags/lu.png b/images/flags/lu.png similarity index 100% rename from chrome/content/images/flags/lu.png rename to images/flags/lu.png diff --git a/chrome/content/images/flags/lv.png b/images/flags/lv.png similarity index 100% rename from chrome/content/images/flags/lv.png rename to images/flags/lv.png diff --git a/chrome/content/images/flags/ly.png b/images/flags/ly.png similarity index 100% rename from chrome/content/images/flags/ly.png rename to images/flags/ly.png diff --git a/chrome/content/images/flags/ma.png b/images/flags/ma.png similarity index 100% rename from chrome/content/images/flags/ma.png rename to images/flags/ma.png diff --git a/chrome/content/images/flags/mc.png b/images/flags/mc.png similarity index 100% rename from chrome/content/images/flags/mc.png rename to images/flags/mc.png diff --git a/chrome/content/images/flags/md.png b/images/flags/md.png similarity index 100% rename from chrome/content/images/flags/md.png rename to images/flags/md.png diff --git a/chrome/content/images/flags/me.png b/images/flags/me.png similarity index 100% rename from chrome/content/images/flags/me.png rename to images/flags/me.png diff --git a/chrome/content/images/flags/mg.png b/images/flags/mg.png similarity index 100% rename from chrome/content/images/flags/mg.png rename to images/flags/mg.png diff --git a/chrome/content/images/flags/mh.png b/images/flags/mh.png similarity index 100% rename from chrome/content/images/flags/mh.png rename to images/flags/mh.png diff --git a/chrome/content/images/flags/mk.png b/images/flags/mk.png similarity index 100% rename from chrome/content/images/flags/mk.png rename to images/flags/mk.png diff --git a/chrome/content/images/flags/ml.png b/images/flags/ml.png similarity index 100% rename from chrome/content/images/flags/ml.png rename to images/flags/ml.png diff --git a/chrome/content/images/flags/mm.png b/images/flags/mm.png similarity index 100% rename from chrome/content/images/flags/mm.png rename to images/flags/mm.png diff --git a/chrome/content/images/flags/mn.png b/images/flags/mn.png similarity index 100% rename from chrome/content/images/flags/mn.png rename to images/flags/mn.png diff --git a/chrome/content/images/flags/mo.png b/images/flags/mo.png similarity index 100% rename from chrome/content/images/flags/mo.png rename to images/flags/mo.png diff --git a/chrome/content/images/flags/mp.png b/images/flags/mp.png similarity index 100% rename from chrome/content/images/flags/mp.png rename to images/flags/mp.png diff --git a/chrome/content/images/flags/mq.png b/images/flags/mq.png similarity index 100% rename from chrome/content/images/flags/mq.png rename to images/flags/mq.png diff --git a/chrome/content/images/flags/mr.png b/images/flags/mr.png similarity index 100% rename from chrome/content/images/flags/mr.png rename to images/flags/mr.png diff --git a/chrome/content/images/flags/ms.png b/images/flags/ms.png similarity index 100% rename from chrome/content/images/flags/ms.png rename to images/flags/ms.png diff --git a/chrome/content/images/flags/mt.png b/images/flags/mt.png similarity index 100% rename from chrome/content/images/flags/mt.png rename to images/flags/mt.png diff --git a/chrome/content/images/flags/mu.png b/images/flags/mu.png similarity index 100% rename from chrome/content/images/flags/mu.png rename to images/flags/mu.png diff --git a/chrome/content/images/flags/mv.png b/images/flags/mv.png similarity index 100% rename from chrome/content/images/flags/mv.png rename to images/flags/mv.png diff --git a/chrome/content/images/flags/mw.png b/images/flags/mw.png similarity index 100% rename from chrome/content/images/flags/mw.png rename to images/flags/mw.png diff --git a/chrome/content/images/flags/mx.png b/images/flags/mx.png similarity index 100% rename from chrome/content/images/flags/mx.png rename to images/flags/mx.png diff --git a/chrome/content/images/flags/my.png b/images/flags/my.png similarity index 100% rename from chrome/content/images/flags/my.png rename to images/flags/my.png diff --git a/chrome/content/images/flags/mz.png b/images/flags/mz.png similarity index 100% rename from chrome/content/images/flags/mz.png rename to images/flags/mz.png diff --git a/chrome/content/images/flags/na.png b/images/flags/na.png similarity index 100% rename from chrome/content/images/flags/na.png rename to images/flags/na.png diff --git a/chrome/content/images/flags/nc.png b/images/flags/nc.png similarity index 100% rename from chrome/content/images/flags/nc.png rename to images/flags/nc.png diff --git a/chrome/content/images/flags/ne.png b/images/flags/ne.png similarity index 100% rename from chrome/content/images/flags/ne.png rename to images/flags/ne.png diff --git a/chrome/content/images/flags/nf.png b/images/flags/nf.png similarity index 100% rename from chrome/content/images/flags/nf.png rename to images/flags/nf.png diff --git a/chrome/content/images/flags/ng.png b/images/flags/ng.png similarity index 100% rename from chrome/content/images/flags/ng.png rename to images/flags/ng.png diff --git a/chrome/content/images/flags/ni.png b/images/flags/ni.png similarity index 100% rename from chrome/content/images/flags/ni.png rename to images/flags/ni.png diff --git a/chrome/content/images/flags/nl.png b/images/flags/nl.png similarity index 100% rename from chrome/content/images/flags/nl.png rename to images/flags/nl.png diff --git a/chrome/content/images/flags/no.png b/images/flags/no.png similarity index 100% rename from chrome/content/images/flags/no.png rename to images/flags/no.png diff --git a/chrome/content/images/flags/np.png b/images/flags/np.png similarity index 100% rename from chrome/content/images/flags/np.png rename to images/flags/np.png diff --git a/chrome/content/images/flags/nr.png b/images/flags/nr.png similarity index 100% rename from chrome/content/images/flags/nr.png rename to images/flags/nr.png diff --git a/chrome/content/images/flags/nu.png b/images/flags/nu.png similarity index 100% rename from chrome/content/images/flags/nu.png rename to images/flags/nu.png diff --git a/chrome/content/images/flags/nz.png b/images/flags/nz.png similarity index 100% rename from chrome/content/images/flags/nz.png rename to images/flags/nz.png diff --git a/chrome/content/images/flags/om.png b/images/flags/om.png similarity index 100% rename from chrome/content/images/flags/om.png rename to images/flags/om.png diff --git a/chrome/content/images/flags/pa.png b/images/flags/pa.png similarity index 100% rename from chrome/content/images/flags/pa.png rename to images/flags/pa.png diff --git a/chrome/content/images/flags/pe.png b/images/flags/pe.png similarity index 100% rename from chrome/content/images/flags/pe.png rename to images/flags/pe.png diff --git a/chrome/content/images/flags/pf.png b/images/flags/pf.png similarity index 100% rename from chrome/content/images/flags/pf.png rename to images/flags/pf.png diff --git a/chrome/content/images/flags/pg.png b/images/flags/pg.png similarity index 100% rename from chrome/content/images/flags/pg.png rename to images/flags/pg.png diff --git a/chrome/content/images/flags/ph.png b/images/flags/ph.png similarity index 100% rename from chrome/content/images/flags/ph.png rename to images/flags/ph.png diff --git a/chrome/content/images/flags/pk.png b/images/flags/pk.png similarity index 100% rename from chrome/content/images/flags/pk.png rename to images/flags/pk.png diff --git a/chrome/content/images/flags/pl.png b/images/flags/pl.png similarity index 100% rename from chrome/content/images/flags/pl.png rename to images/flags/pl.png diff --git a/chrome/content/images/flags/pm.png b/images/flags/pm.png similarity index 100% rename from chrome/content/images/flags/pm.png rename to images/flags/pm.png diff --git a/chrome/content/images/flags/pn.png b/images/flags/pn.png similarity index 100% rename from chrome/content/images/flags/pn.png rename to images/flags/pn.png diff --git a/chrome/content/images/flags/pr.png b/images/flags/pr.png similarity index 100% rename from chrome/content/images/flags/pr.png rename to images/flags/pr.png diff --git a/chrome/content/images/flags/ps.png b/images/flags/ps.png similarity index 100% rename from chrome/content/images/flags/ps.png rename to images/flags/ps.png diff --git a/chrome/content/images/flags/pt.png b/images/flags/pt.png similarity index 100% rename from chrome/content/images/flags/pt.png rename to images/flags/pt.png diff --git a/chrome/content/images/flags/pw.png b/images/flags/pw.png similarity index 100% rename from chrome/content/images/flags/pw.png rename to images/flags/pw.png diff --git a/chrome/content/images/flags/py.png b/images/flags/py.png similarity index 100% rename from chrome/content/images/flags/py.png rename to images/flags/py.png diff --git a/chrome/content/images/flags/qa.png b/images/flags/qa.png similarity index 100% rename from chrome/content/images/flags/qa.png rename to images/flags/qa.png diff --git a/chrome/content/images/flags/re.png b/images/flags/re.png similarity index 100% rename from chrome/content/images/flags/re.png rename to images/flags/re.png diff --git a/chrome/content/images/flags/ro.png b/images/flags/ro.png similarity index 100% rename from chrome/content/images/flags/ro.png rename to images/flags/ro.png diff --git a/chrome/content/images/flags/rs.png b/images/flags/rs.png similarity index 100% rename from chrome/content/images/flags/rs.png rename to images/flags/rs.png diff --git a/chrome/content/images/flags/ru.png b/images/flags/ru.png similarity index 100% rename from chrome/content/images/flags/ru.png rename to images/flags/ru.png diff --git a/chrome/content/images/flags/rw.png b/images/flags/rw.png similarity index 100% rename from chrome/content/images/flags/rw.png rename to images/flags/rw.png diff --git a/chrome/content/images/flags/sa.png b/images/flags/sa.png similarity index 100% rename from chrome/content/images/flags/sa.png rename to images/flags/sa.png diff --git a/chrome/content/images/flags/sb.png b/images/flags/sb.png similarity index 100% rename from chrome/content/images/flags/sb.png rename to images/flags/sb.png diff --git a/chrome/content/images/flags/sc.png b/images/flags/sc.png similarity index 100% rename from chrome/content/images/flags/sc.png rename to images/flags/sc.png diff --git a/chrome/content/images/flags/scotland.png b/images/flags/scotland.png similarity index 100% rename from chrome/content/images/flags/scotland.png rename to images/flags/scotland.png diff --git a/chrome/content/images/flags/sd.png b/images/flags/sd.png similarity index 100% rename from chrome/content/images/flags/sd.png rename to images/flags/sd.png diff --git a/chrome/content/images/flags/se.png b/images/flags/se.png similarity index 100% rename from chrome/content/images/flags/se.png rename to images/flags/se.png diff --git a/chrome/content/images/flags/sg.png b/images/flags/sg.png similarity index 100% rename from chrome/content/images/flags/sg.png rename to images/flags/sg.png diff --git a/chrome/content/images/flags/sh.png b/images/flags/sh.png similarity index 100% rename from chrome/content/images/flags/sh.png rename to images/flags/sh.png diff --git a/chrome/content/images/flags/si.png b/images/flags/si.png similarity index 100% rename from chrome/content/images/flags/si.png rename to images/flags/si.png diff --git a/chrome/content/images/flags/sj.png b/images/flags/sj.png similarity index 100% rename from chrome/content/images/flags/sj.png rename to images/flags/sj.png diff --git a/chrome/content/images/flags/sk.png b/images/flags/sk.png similarity index 100% rename from chrome/content/images/flags/sk.png rename to images/flags/sk.png diff --git a/chrome/content/images/flags/sl.png b/images/flags/sl.png similarity index 100% rename from chrome/content/images/flags/sl.png rename to images/flags/sl.png diff --git a/chrome/content/images/flags/sm.png b/images/flags/sm.png similarity index 100% rename from chrome/content/images/flags/sm.png rename to images/flags/sm.png diff --git a/chrome/content/images/flags/sn.png b/images/flags/sn.png similarity index 100% rename from chrome/content/images/flags/sn.png rename to images/flags/sn.png diff --git a/chrome/content/images/flags/so.png b/images/flags/so.png similarity index 100% rename from chrome/content/images/flags/so.png rename to images/flags/so.png diff --git a/chrome/content/images/flags/sr.png b/images/flags/sr.png similarity index 100% rename from chrome/content/images/flags/sr.png rename to images/flags/sr.png diff --git a/chrome/content/images/flags/st.png b/images/flags/st.png similarity index 100% rename from chrome/content/images/flags/st.png rename to images/flags/st.png diff --git a/chrome/content/images/flags/sv.png b/images/flags/sv.png similarity index 100% rename from chrome/content/images/flags/sv.png rename to images/flags/sv.png diff --git a/chrome/content/images/flags/sy.png b/images/flags/sy.png similarity index 100% rename from chrome/content/images/flags/sy.png rename to images/flags/sy.png diff --git a/chrome/content/images/flags/sz.png b/images/flags/sz.png similarity index 100% rename from chrome/content/images/flags/sz.png rename to images/flags/sz.png diff --git a/chrome/content/images/flags/tc.png b/images/flags/tc.png similarity index 100% rename from chrome/content/images/flags/tc.png rename to images/flags/tc.png diff --git a/chrome/content/images/flags/td.png b/images/flags/td.png similarity index 100% rename from chrome/content/images/flags/td.png rename to images/flags/td.png diff --git a/chrome/content/images/flags/tf.png b/images/flags/tf.png similarity index 100% rename from chrome/content/images/flags/tf.png rename to images/flags/tf.png diff --git a/chrome/content/images/flags/tg.png b/images/flags/tg.png similarity index 100% rename from chrome/content/images/flags/tg.png rename to images/flags/tg.png diff --git a/chrome/content/images/flags/th.png b/images/flags/th.png similarity index 100% rename from chrome/content/images/flags/th.png rename to images/flags/th.png diff --git a/chrome/content/images/flags/tj.png b/images/flags/tj.png similarity index 100% rename from chrome/content/images/flags/tj.png rename to images/flags/tj.png diff --git a/chrome/content/images/flags/tk.png b/images/flags/tk.png similarity index 100% rename from chrome/content/images/flags/tk.png rename to images/flags/tk.png diff --git a/chrome/content/images/flags/tl.png b/images/flags/tl.png similarity index 100% rename from chrome/content/images/flags/tl.png rename to images/flags/tl.png diff --git a/chrome/content/images/flags/tm.png b/images/flags/tm.png similarity index 100% rename from chrome/content/images/flags/tm.png rename to images/flags/tm.png diff --git a/chrome/content/images/flags/tn.png b/images/flags/tn.png similarity index 100% rename from chrome/content/images/flags/tn.png rename to images/flags/tn.png diff --git a/chrome/content/images/flags/to.png b/images/flags/to.png similarity index 100% rename from chrome/content/images/flags/to.png rename to images/flags/to.png diff --git a/chrome/content/images/flags/tr.png b/images/flags/tr.png similarity index 100% rename from chrome/content/images/flags/tr.png rename to images/flags/tr.png diff --git a/chrome/content/images/flags/tt.png b/images/flags/tt.png similarity index 100% rename from chrome/content/images/flags/tt.png rename to images/flags/tt.png diff --git a/chrome/content/images/flags/tv.png b/images/flags/tv.png similarity index 100% rename from chrome/content/images/flags/tv.png rename to images/flags/tv.png diff --git a/chrome/content/images/flags/tw.png b/images/flags/tw.png similarity index 100% rename from chrome/content/images/flags/tw.png rename to images/flags/tw.png diff --git a/chrome/content/images/flags/tz.png b/images/flags/tz.png similarity index 100% rename from chrome/content/images/flags/tz.png rename to images/flags/tz.png diff --git a/chrome/content/images/flags/ua.png b/images/flags/ua.png similarity index 100% rename from chrome/content/images/flags/ua.png rename to images/flags/ua.png diff --git a/chrome/content/images/flags/ug.png b/images/flags/ug.png similarity index 100% rename from chrome/content/images/flags/ug.png rename to images/flags/ug.png diff --git a/chrome/content/images/flags/um.png b/images/flags/um.png similarity index 100% rename from chrome/content/images/flags/um.png rename to images/flags/um.png diff --git a/chrome/content/images/flags/us.png b/images/flags/us.png similarity index 100% rename from chrome/content/images/flags/us.png rename to images/flags/us.png diff --git a/chrome/content/images/flags/uy.png b/images/flags/uy.png similarity index 100% rename from chrome/content/images/flags/uy.png rename to images/flags/uy.png diff --git a/chrome/content/images/flags/uz.png b/images/flags/uz.png similarity index 100% rename from chrome/content/images/flags/uz.png rename to images/flags/uz.png diff --git a/chrome/content/images/flags/va.png b/images/flags/va.png similarity index 100% rename from chrome/content/images/flags/va.png rename to images/flags/va.png diff --git a/chrome/content/images/flags/vc.png b/images/flags/vc.png similarity index 100% rename from chrome/content/images/flags/vc.png rename to images/flags/vc.png diff --git a/chrome/content/images/flags/ve.png b/images/flags/ve.png similarity index 100% rename from chrome/content/images/flags/ve.png rename to images/flags/ve.png diff --git a/chrome/content/images/flags/vg.png b/images/flags/vg.png similarity index 100% rename from chrome/content/images/flags/vg.png rename to images/flags/vg.png diff --git a/chrome/content/images/flags/vi.png b/images/flags/vi.png similarity index 100% rename from chrome/content/images/flags/vi.png rename to images/flags/vi.png diff --git a/chrome/content/images/flags/vn.png b/images/flags/vn.png similarity index 100% rename from chrome/content/images/flags/vn.png rename to images/flags/vn.png diff --git a/chrome/content/images/flags/vu.png b/images/flags/vu.png similarity index 100% rename from chrome/content/images/flags/vu.png rename to images/flags/vu.png diff --git a/chrome/content/images/flags/wales.png b/images/flags/wales.png similarity index 100% rename from chrome/content/images/flags/wales.png rename to images/flags/wales.png diff --git a/chrome/content/images/flags/wf.png b/images/flags/wf.png similarity index 100% rename from chrome/content/images/flags/wf.png rename to images/flags/wf.png diff --git a/chrome/content/images/flags/ws.png b/images/flags/ws.png similarity index 100% rename from chrome/content/images/flags/ws.png rename to images/flags/ws.png diff --git a/chrome/content/images/flags/ye.png b/images/flags/ye.png similarity index 100% rename from chrome/content/images/flags/ye.png rename to images/flags/ye.png diff --git a/chrome/content/images/flags/yt.png b/images/flags/yt.png similarity index 100% rename from chrome/content/images/flags/yt.png rename to images/flags/yt.png diff --git a/chrome/content/images/flags/za.png b/images/flags/za.png similarity index 100% rename from chrome/content/images/flags/za.png rename to images/flags/za.png diff --git a/chrome/content/images/flags/zm.png b/images/flags/zm.png similarity index 100% rename from chrome/content/images/flags/zm.png rename to images/flags/zm.png diff --git a/chrome/content/images/flags/zw.png b/images/flags/zw.png similarity index 100% rename from chrome/content/images/flags/zw.png rename to images/flags/zw.png diff --git a/chrome/content/images/help.png b/images/help.png similarity index 100% rename from chrome/content/images/help.png rename to images/help.png diff --git a/chrome/content/images/hop.svg b/images/hop.svg similarity index 100% rename from chrome/content/images/hop.svg rename to images/hop.svg diff --git a/chrome/content/images/host.png b/images/host.png similarity index 100% rename from chrome/content/images/host.png rename to images/host.png diff --git a/chrome/content/images/info.png b/images/info.png similarity index 100% rename from chrome/content/images/info.png rename to images/info.png diff --git a/chrome/content/images/ipv6.svg b/images/ipv6.svg similarity index 100% rename from chrome/content/images/ipv6.svg rename to images/ipv6.svg diff --git a/chrome/content/images/loader.gif b/images/loader.gif similarity index 100% rename from chrome/content/images/loader.gif rename to images/loader.gif diff --git a/chrome/content/images/local.png b/images/local.png similarity index 100% rename from chrome/content/images/local.png rename to images/local.png diff --git a/chrome/content/images/mailhops-logo.png b/images/mailhops-logo.png similarity index 100% rename from chrome/content/images/mailhops-logo.png rename to images/mailhops-logo.png diff --git a/chrome/content/images/mailhops-logo.svg b/images/mailhops-logo.svg similarity index 100% rename from chrome/content/images/mailhops-logo.svg rename to images/mailhops-logo.svg diff --git a/chrome/content/images/mailhops16.png b/images/mailhops16.png similarity index 100% rename from chrome/content/images/mailhops16.png rename to images/mailhops16.png diff --git a/chrome/content/images/mailhops24.png b/images/mailhops24.png similarity index 100% rename from chrome/content/images/mailhops24.png rename to images/mailhops24.png diff --git a/chrome/content/images/mailhops32.png b/images/mailhops32.png similarity index 100% rename from chrome/content/images/mailhops32.png rename to images/mailhops32.png diff --git a/chrome/content/images/refresh.png b/images/refresh.png similarity index 100% rename from chrome/content/images/refresh.png rename to images/refresh.png diff --git a/images/screenshot-tb78-preferences.png b/images/screenshot-tb78-preferences.png new file mode 100644 index 0000000..8873899 Binary files /dev/null and b/images/screenshot-tb78-preferences.png differ diff --git a/images/screenshot-tb78-view.png b/images/screenshot-tb78-view.png new file mode 100644 index 0000000..8f07a14 Binary files /dev/null and b/images/screenshot-tb78-view.png differ diff --git a/chrome/content/images/w3w.png b/images/w3w.png similarity index 100% rename from chrome/content/images/w3w.png rename to images/w3w.png diff --git a/chrome/content/images/weather/clear.png b/images/weather/clear.png similarity index 100% rename from chrome/content/images/weather/clear.png rename to images/weather/clear.png diff --git a/chrome/content/images/weather/clear_night.png b/images/weather/clear_night.png similarity index 100% rename from chrome/content/images/weather/clear_night.png rename to images/weather/clear_night.png diff --git a/chrome/content/images/weather/clouds.png b/images/weather/clouds.png similarity index 100% rename from chrome/content/images/weather/clouds.png rename to images/weather/clouds.png diff --git a/chrome/content/images/weather/cloudy.png b/images/weather/cloudy.png similarity index 100% rename from chrome/content/images/weather/cloudy.png rename to images/weather/cloudy.png diff --git a/chrome/content/images/weather/cloudy_night.png b/images/weather/cloudy_night.png similarity index 100% rename from chrome/content/images/weather/cloudy_night.png rename to images/weather/cloudy_night.png diff --git a/chrome/content/images/weather/lightning.png b/images/weather/lightning.png similarity index 100% rename from chrome/content/images/weather/lightning.png rename to images/weather/lightning.png diff --git a/chrome/content/images/weather/rain.png b/images/weather/rain.png similarity index 100% rename from chrome/content/images/weather/rain.png rename to images/weather/rain.png diff --git a/chrome/content/images/weather/snow.png b/images/weather/snow.png similarity index 100% rename from chrome/content/images/weather/snow.png rename to images/weather/snow.png diff --git a/chrome/content/images/weather/sun.png b/images/weather/sun.png similarity index 100% rename from chrome/content/images/weather/sun.png rename to images/weather/sun.png diff --git a/js/bootstrap.js b/js/bootstrap.js new file mode 100644 index 0000000..cda6f41 --- /dev/null +++ b/js/bootstrap.js @@ -0,0 +1,47 @@ +// messenger.messages.onNewMailReceived.addListener((folder, messageList) => { +// if(messageList.messages.length){ +// for (var m = 0; m < messageList.messages.length; m++){ +// browser.messages.getFull(messageList.messages[m].id).then((messagePart) => { +// MailHops.getRoute(messageList.messages[m].id, messagePart.headers); +// }); +// } +// } +// }); + +browser.messageDisplayAction.onClicked.addListener((tabId) => { + if (MailHops.isLoaded) { + browser.messageDisplayAction.setPopup({popup: "content/mailhops_details.xhtml"}); + browser.messageDisplayAction.openPopup(); + } +}); + +messenger.messageDisplay.onMessageDisplayed.addListener((tabId, message) => { + + messenger.messages.getFull(message.id).then((messagePart) => { + // get route + MailHops.message.id = message.id; + MailHops.message.headers = messagePart.headers; + MailHops.message.display = true; + MailHops.getRoute(); + }); + +}); + +var port; +function connected(p) { + port = p; + port.onMessage.addListener(function(m) { + switch (m.command) { + case 'details': + port.postMessage({ + "cmd": m.command, + "message": MailHops.message, + "response": MailHops.response, + "meta": MailHops.meta, + "unit": MailHops.unit + }); + break; + } + }); +} +browser.runtime.onConnect.addListener(connected); \ No newline at end of file diff --git a/js/experiment_apis.js b/js/experiment_apis.js new file mode 100644 index 0000000..c0b672e --- /dev/null +++ b/js/experiment_apis.js @@ -0,0 +1,82 @@ +var { ExtensionCommon } = ChromeUtils.import("resource://gre/modules/ExtensionCommon.jsm"); +var { Services } = ChromeUtils.import("resource://gre/modules/Services.jsm"); +const ehb = "expandedHeadersBottomBox"; +const eh2 = "expandedHeaders2"; +const win = Services.wm.getMostRecentWindow("mail:3pane"); +const win2 = Services.wm.getMostRecentWindow("mail:messageWindow"); + +const mailHopsUI = class extends ExtensionCommon.ExtensionAPI { + getAPI(context) { + context.callOnClose(this); + return { + mailHopsUI: { + insert(wd, basePath, iconPath, iconText, id, target) { + let elm = wd.document.getElementById(target); + const compact = "compact"; + let iconSize = 48, marginTop = 0; + if (wd.document.getElementById(eh2).getAttribute(compact) == compact) { + iconSize = 32, marginTop = -16; + } + let mailHops = wd.document.getElementById(id); + if (mailHops) { + mailHops.setAttribute("image", basePath + iconPath); + mailHops.setAttribute("tooltiptext", iconText); + mailHops.setAttribute("style", "flex-shrink: 0; padding: 0; margin:" + marginTop + "px 2px 0 2px"); + for (let elm of mailHops.children) { + if (elm.nodeName == "image") { + elm.width = iconSize; + elm.height = iconSize; + elm.setAttribute("style", "margin: 0 2px 0 2px"); + break; + } + } + } else { + let mailHops = wd.document.createXULElement("toolbarbutton"); + mailHops.id = id; + mailHops.setAttribute("image", basePath + iconPath); + mailHops.setAttribute("tooltiptext", iconText); + mailHops.setAttribute("style", "flex-shrink: 0; padding: 0; margin:" + marginTop + "px 2px 0 2px"); + mailHops.addEventListener("click", () => { + wd.document.getElementById("mailhops-messageDisplayAction-toolbarbutton").click(); + }, false); + wd.document.getElementById(ehb).insertBefore(mailHops, elm); + for (let elm of mailHops.children) { + if (elm.nodeName == "image") { + elm.width = iconSize; + elm.height = iconSize; + elm.setAttribute("style", "margin: 0 2px 0 2px"); + break; + } + } + } + }, + mv(wd, id, target) { + let mailHops = wd.document.getElementById(id); + let elm = wd.document.getElementById(target); + wd.document.getElementById(ehb).insertBefore(mailHops, elm); + }, + rm(wd, id) { + if (wd.document.getElementById(id)) wd.document.getElementById(id).remove(); + }, + async insertBefore(basePath, iconPath, iconText, id, target) { + this.insert(win, basePath, iconPath, iconText, id, target); + if (win2) { + this.insert(win2, basePath, iconPath, iconText, id, target); + } + }, + async move(id, target) { + this.mv(win, id, target); + if (win2) this.mv(win2, id, target); + }, + async remove(id) { + this.rm(win, id); + if (win2) this.rm(win2, id); + } + } + } + } + close() { + let id = "countryIcon"; + if (win.document.getElementById(id)) win.document.getElementById(id).remove(); + } +}; \ No newline at end of file diff --git a/js/mailhops.js b/js/mailhops.js new file mode 100644 index 0000000..1d29070 --- /dev/null +++ b/js/mailhops.js @@ -0,0 +1,364 @@ +/* +* @author: Andrew Van Tassel +* @email: andrew@andrewvantassel.com +* @website: http://Mailhops.com +*/ + +const MailHops = { + msgURI: null, + isLoaded: false, + options: { + version: 'MailHops Plugin 4.0.0', + api_key: '', + owm_key: '', + lang: 'en', + unit: 'mi', + api_http: 'https://', + api_host: 'api.Mailhops.com', + debug: true, + country_tag: false, + travel_time_junk: false, + country_filter: [] + }, + message: { + id: null + , map_url: '' + , time: null + , secure: [] + , headers: [] + , auth: [] + , sender: { + icon: '/images/refresh.png' + , title: 'Loading...' + , description: '' + } + }, + response: {}, + meta: {} +}; + +MailHops.LOG = function(msg) { + if(!MailHops.options.debug) + return; + console.log('MailHops', msg); +}; + +MailHops.init = function(reload) +{ + var getting = browser.storage.local.get(); + getting.then(data => { + if (data.api_key) { + MailHops.options.api_key = data.api_key; + } + if (data.owm_key) { + MailHops.options.owm_key = data.owm_key; + } + if (data.lang) { + MailHops.options.lang = data.lang; + } + if (data.unit) { + MailHops.options.unit = data.unit; + } + MailHops.LOG('load MailHops prefs'); + }, error => { + MailHops.LOG('Error loading MailHops prefs'); + }); +}; + +MailHops.getRoute = function () { + // set loading icon + browser.messageDisplayAction.setPopup({ popup: '' }); + browser.messageDisplayAction.setIcon({ path: '/images/refresh.png' }); + browser.messageDisplayAction.setTitle({ title: 'Loading...' }); + if(browser.mailHopsUI) + browser.mailHopsUI.insertBefore("", '/images/refresh.png', '', "countryIcon", "expandedHeaders2"); + + //IP regex + var regexIp=/(1\d{0,2}|2(?:[0-4]\d{0,1}|[6789]|5[0-5]?)?|[3-9]\d?|0)\.(1\d{0,2}|2(?:[0-4]\d{0,1}|[6789]|5[0-5]?)?|[3-9]\d?|0)\.(1\d{0,2}|2(?:[0-4]\d{0,1}|[6789]|5[0-5]?)?|[3-9]\d?|0)\.(1\d{0,2}|2(?:[0-4]\d{0,1}|[6789]|5[0-5]?)?|[3-9]\d?|0)(\/(?:[012]\d?|3[012]?|[456789])){0,1}$/; + var regexAllIp = /(1\d{0,2}|2(?:[0-4]\d{0,1}|[6789]|5[0-5]?)?|[3-9]\d?|0)\.(1\d{0,2}|2(?:[0-4]\d{0,1}|[6789]|5[0-5]?)?|[3-9]\d?|0)\.(1\d{0,2}|2(?:[0-4]\d{0,1}|[6789]|5[0-5]?)?|[3-9]\d?|0)\.(1\d{0,2}|2(?:[0-4]\d{0,1}|[6789]|5[0-5]?)?|[3-9]\d?|0)(\/(?:[012]\d?|3[012]?|[456789])){0,1}/g; + var regexIPV6 = /s*((([0-9A-Fa-f]{1,4}:){7}([0-9A-Fa-f]{1,4}|:))|(([0-9A-Fa-f]{1,4}:){6}(:[0-9A-Fa-f]{1,4}|((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3})|:))|(([0-9A-Fa-f]{1,4}:){5}(((:[0-9A-Fa-f]{1,4}){1,2})|:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3})|:))|(([0-9A-Fa-f]{1,4}:){4}(((:[0-9A-Fa-f]{1,4}){1,3})|((:[0-9A-Fa-f]{1,4})?:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){3}(((:[0-9A-Fa-f]{1,4}){1,4})|((:[0-9A-Fa-f]{1,4}){0,2}:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){2}(((:[0-9A-Fa-f]{1,4}){1,5})|((:[0-9A-Fa-f]{1,4}){0,3}:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){1}(((:[0-9A-Fa-f]{1,4}){1,6})|((:[0-9A-Fa-f]{1,4}){0,4}:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:))|(:(((:[0-9A-Fa-f]{1,4}){1,7})|((:[0-9A-Fa-f]{1,4}){0,5}:((25[0-5]|2[0-4]d|1dd|[1-9]?d)(.(25[0-5]|2[0-4]d|1dd|[1-9]?d)){3}))|:)))(%.+)?s*/g; + + var headReceived = MailHops.message.headers['received'] || []; + var headDate = MailHops.message.headers['date'] ? MailHops.message.headers['date'][0] : ''; + var headXReceived = MailHops.message.headers['x-received'] ? MailHops.message.headers['x-received'][0] : ''; + var headXOrigIP = MailHops.message.headers['x-originating-ip'] ? MailHops.message.headers['x-originating-ip'][0] : ''; + // auth box + var headXMailer = MailHops.message.headers['x-mailer'] ? MailHops.message.headers['x-mailer'][0] : ''; + var headUserAgent = MailHops.message.headers['user-agent'] ? MailHops.message.headers['user-agent'][0] : ''; + var headXMimeOLE = MailHops.message.headers['x-mimeole'] ? MailHops.message.headers['x-mimeole'][0] : ''; + var headReceivedSPF = MailHops.message.headers['received-spf'] ? MailHops.message.headers['received-spf'][0] : ''; + var headAuth = MailHops.message.headers['authentication-results'] ? MailHops.message.headers['authentication-results'][0] : ''; + var headListUnsubscribe = MailHops.message.headers['list-unsubscribe'] ? MailHops.message.headers['list-unsubscribe'][0] : ''; + + var all_ips = new Array(); + var rline = '',firstDate=headDate,lastDate; + //empty secure and time + MailHops.message.secure = []; + MailHops.message.time = null; + MailHops.message.auth = MailHops.auth( headXMailer, headUserAgent, headXMimeOLE, headAuth, headReceivedSPF ); + + //loop through the received headers and parse for IP addresses + if (Boolean(headReceived)){ + var received_ips = new Array(); + for( var h=0; h < headReceived.length; h++ ) { + //build the received line by concat until semi-colon ; date/time + rline += headReceived[h]; + if(headReceived[h].indexOf(';') === -1) + continue; + // first and last dates are used to calculate time traveled + if(rline.indexOf(';') !== -1){ + if(!firstDate) + firstDate = rline.substring(rline.indexOf(';')+1).trim(); + if(!lastDate) + lastDate = rline.substring(rline.indexOf(';')+1).trim(); + } + + // IPV6 check + rline = rline.replace(/\[IPv6\:/g,'['); + if(rline.match(regexIPV6)){ + all_ips.unshift( rline.match(regexIPV6)[0] ); + //reset the line + rline=''; + continue; + } + // parse IPs out of Received line + received_ips = rline.match(regexAllIp); + //continue if no IPs found + if(!received_ips){ + //reset the line + rline=''; + continue; + } + //get unique IPs for each Received header + received_ips = received_ips.filter(function(item, pos) { + return received_ips.indexOf(item) === pos; + }); + for( var r=received_ips.length; r >= 0 ; r-- ){ + if(regexIp.test(received_ips[r]) && MailHops.testIP(received_ips[r],rline)){ + all_ips.unshift( received_ips[r] ); + } + } + //reset the line + rline=''; + } + } + + // parse dates + if(firstDate && firstDate.indexOf('(') !==- 1) + firstDate = firstDate.substring(0,firstDate.indexOf('(')).trim(); + if(lastDate && lastDate.indexOf('(') !== -1) + lastDate = lastDate.substring(0,lastDate.indexOf('(')).trim(); + if(firstDate && lastDate){ + try { + firstDate = new Date(firstDate); + lastDate = new Date(lastDate); + MailHops.message.time = lastDate - firstDate; + } catch(e){ + MailHops.LOG('travel dates parse Error: '+JSON.stringify(e)); + MailHops.message.time = null; + } + } else { + MailHops.message.time = null; + } + + //get the originating IP address + if(Boolean(headXOrigIP)){ + headXOrigIP = headXOrigIP.replace(/\[IPv6\:/g,'['); + //IPV6 check + if(headXOrigIP.match(regexIPV6)){ + var ip = headXOrigIP.match(regexIPV6) + if(Boolean(ip) && ip.length && all_ips.indexOf(ip[0])==-1) + all_ips.unshift( ip[0] ); + } else { + var ip = headXOrigIP.match(regexAllIp); + if(Boolean(ip) && ip.length && all_ips.indexOf(ip[0])==-1) + all_ips.unshift( ip[0] ); + } + } + + if ( all_ips.length ){ + MailHops.lookupRoute ( all_ips ) ; + } else { + MailHops.clear(); + } +}; + +//another ip check, dates will throw off the regex +MailHops.testIP = function(ip,header){ + var validIP = true; + + try { + var firstchar = header.substring(header.indexOf(ip)-1); + firstchar = firstchar.substring(0,1); + var lastchar = header.substring((header.indexOf(ip)+ip.length)); + lastchar = lastchar.substring(0,1); + + if(firstchar.match(/\.|\d|\-/) + || lastchar.match(/\.|\d|\-/) + || ( firstchar == '?' && lastchar == '?' ) + || (firstchar == ':' || lastchar == ':') + || lastchar == ';' + || header.toLowerCase().indexOf(' id '+ip) !== -1 + || parseInt(ip.substring(0,ip.indexOf('.'))) >= 240 //IANA-RESERVED + ){ + //only if there is one instance of this IP + if(header.indexOf(ip) == header.lastIndexOf(ip)) + validIP = false; + } else if(header.indexOf('using SSL') !== -1 + || header.indexOf('using TLS') !== -1 + || header.indexOf('version=TLSv1/SSLv3') !== -1 + ){ + //check if this IP was part of a secure transmission + MailHops.message.secure.push(ip); + } + } catch(e) { + MailHops.LOG('testIP Error: '+JSON.stringify(e)); + } + return validIP; +}; + +MailHops.clear = function () { + MailHops.message.sender = { + title: 'Local', + countryCode: '', + icon: '/images/local.png' + }; + browser.messageDisplayAction.setIcon({ path: MailHops.message.sender.icon }); + browser.messageDisplayAction.setTitle({ title: MailHops.message.sender.title }); + if (browser.mailHopsUI) + browser.mailHopsUI.insertBefore("", MailHops.message.sender.icon, MailHops.message.sender.title, "countryIcon", "expandedHeaders2"); +} + +MailHops.error = function(status, data){ + MailHops.message.sender = { + title: (data && data.error && data.error.message) ? data && data.error.message : 'Service Unavailable', + countryCode: '', + icon: '/images/auth/error.png' + }; + browser.messageDisplayAction.setIcon({ path: MailHops.message.sender.icon }); + browser.messageDisplayAction.setTitle({ title: MailHops.message.sender.title }); + if (browser.mailHopsUI) + browser.mailHopsUI.insertBefore("", MailHops.message.sender.icon, MailHops.message.sender.title, "countryIcon", "expandedHeaders2"); +} + +MailHops.auth = function (header_xmailer, header_useragent, header_xmimeole, header_auth, header_spf) { + let auth = []; + //SPF + if(header_spf){ + header_spf = header_spf.replace(/^\s+/, ""); + auth.push({ + type: 'SPF', + icon: '/images/auth/' + headerSPFArr[0] + '.png', + copy: header_spf + '\n' + mailHopsUtils.spf(headerSPFArr[0]) + }); + } + //Authentication-Results + //http://tools.ietf.org/html/rfc5451 + if(header_auth){ + var headerAuthArr=header_auth.split(';'); + var dkim_result; + var spf_result; + for(var h=0;h 10000){ + messenger.messages.update(MailHops.message.id, { 'junk': true }); + MailHops.LOG( "Junk: Travel time match" ); + } + } catch(e){ + MailHops.LOG("Error adding CountryCode tag: " + e); + } +}; + +MailHops.init(); \ No newline at end of file diff --git a/js/mailhops_details.js b/js/mailhops_details.js new file mode 100644 index 0000000..cdbc221 --- /dev/null +++ b/js/mailhops_details.js @@ -0,0 +1,106 @@ +var port = browser.runtime.connect({ name: "MailHops" }); +port.postMessage({ command: "details" }); + +port.onMessage.addListener(function(msg) { + updateContent(msg); + console.log(msg.message.map_url) + document.getElementById("mh-map-button").addEventListener("click", function () { + browser.tabs.create({ url: msg.message.map_url }); + }); +}); + +document.getElementById("mh-options-button").addEventListener("click", function () { + browser.tabs.create({ url: '/content/preferences.html' }); +}); + +document.getElementById("mh-close-button").addEventListener("click", function () { + setTimeout(function () { + window.close(); + }, 10); +}); + +function updateContent(msg) { + + const route = msg.response.route || []; + const sender = msg.message.sender || null; + const unit = msg.unit || "mi"; + let client = null; + let items = []; + + for (var i = 0; i < route.length; i++) { + var header = 'Private'; + var icon = '/images/local.png'; + var distance = ''; + // set the client route + if (route[i].client) + client = route[i]; + + if(route[i].countryCode) + icon = '/images/flags/' + route[i].countryCode.toLowerCase() + '.png'; + + if(route[i].city && route[i].state) + header = route[i].city + ', ' + route[i].state; + else if(route[i].city && route[i].countryCode) + header = route[i].city + ', ' + route[i].countryCode; + else if (route[i].city) + header = route[i].city; + else if (route[i].state) + header = route[i].state; + else if (route[i].countryName) + header = route[i].countryName; + + var description = '' + route[i].ip + ''; + + if (msg.message.secure.indexOf(route[i].ip) !== -1) { + description += ''; + } + + if (route[i].host) + description += route[i].host; + if (route[i].whois && route[i].whois.descr) + description += route[i].whois.descr; + if (route[i].whois && route[i].whois.netname) + description += route[i].whois.netname; + + var weather = ''; + if (route[i].weather) { + weather = ' '; + weather += Math.round(route[i].weather.temp).toString() + '°' + route[i].weather.temp_unit+' '; + weather += route[i].weather.summary; + } + + var asn = ''; + if (route[i].asn) { + asn = 'ASN Org: ' + route[i].asn.autonomous_system_organization; + asn += ' (' + route[i].asn.autonomous_system_number + ')' + } + + var auth = ''; + if (msg.message.auth.length) { + for (var a = 0; a < msg.message.auth.length; a++){ + auth += '' + msg.message.auth[a].type + ' ' + msg.message.auth[a].copy + ''; + } + } + // append child + items.push('\ + \ + ' + header + weather +' '+ (i + 1) +'\ + '+ description + asn + '\ + \ + '); + } + // header + document.getElementById('hop-message-header').innerHTML = `${route.length} Hops`; + if (sender && client) { + document.getElementById('hop-message-header').innerHTML += ' over '+MailHopsUtils.getDistance(sender, client, unit) + ' ' + unit; + } + // hop list + document.getElementById('hop-list').innerHTML = items.join('') + distance; + +} + +function doOpenURL(url) { + if (url) { + browser.tabs.create({ url: url }); + } +} diff --git a/js/preferences.js b/js/preferences.js new file mode 100644 index 0000000..d8d48f2 --- /dev/null +++ b/js/preferences.js @@ -0,0 +1,98 @@ +var mailHopPreferences = { + api_key: '', //api key + valid_api_key: false, + owm_key: '', //OpenWeatherMap.org api key + + loadPreferences: function(){ + var self = this; + this.api_key = document.getElementById("mailhop.api_key"); + this.owm_key = document.getElementById("mailhop.owm_key"); + + document.getElementById("save").addEventListener("click", function () { + self.saveAPIKey(); + }); + + var getting = browser.storage.local.get(); + getting.then(data => { + if (data.api_key) { + self.api_key.value = data.api_key; + document.getElementById("join-link").innerHTML = 'My Account'; + document.getElementById("join-link").setAttribute('href','https://mailhops.com/account/'+data.api_key); + } + if (data.owm_key) { + self.owm_key.value = data.owm_key; + } + }, error => { + self.planError(JSON.stringify(error)); + }); + }, + + savePreferences: function () { + var self = this; + browser.storage.local.set({ + api_key: self.api_key.value.trim(), + owm_key: self.owm_key.value.trim() + }); + return true; + }, + + planError: function(error){ + this.valid_api_key=false; + document.getElementById("plan-error").style.display = 'block'; + document.getElementById("plan-error").innerHTML = error; + document.getElementById("plan").innerHTML = ''; + document.getElementById("status").innerHTML = ''; + document.getElementById("rate-limit").innerHTML = ''; + document.getElementById("rate-remaining").innerHTML = ''; + document.getElementById("rate-reset").innerHTML = ''; + }, + saveAPIKey: function() { + if(Boolean(this.api_key) && this.api_key.value != ''){ + var xmlhttp = new XMLHttpRequest(); + var apiBase = 'https://api.mailhops.com', + accountURL = '/v2/accounts/?api_key='+this.api_key.value.trim(), + api_key = this.api_key.value.trim(), + self = this; + + xmlhttp.open("GET", apiBase+accountURL, true); + xmlhttp.onreadystatechange=function() { + if (xmlhttp.readyState===4) { + try { + var data = JSON.parse(xmlhttp.responseText); + if(xmlhttp.status===200){ + self.valid_api_key=true; + document.getElementById("plan-error").style.display = 'none'; + // set plan info + document.getElementById("plan").innerHTML = "Plan: "+data.account.subscriptions.data[0].plan.name; + document.getElementById("status").innerHTML = "Status: "+data.account.subscriptions.data[0].status; + document.getElementById("rate-limit").innerHTML = "Limit: "+data.account.rate.limit; + document.getElementById("rate-remaining").innerHTML = "Remaining: "+data.account.rate.remaining; + if(data.account.rate.reset/60 < 60) + document.getElementById("rate-reset").innerHTML = "Resets in: "+Math.round(data.account.rate.reset/60)+" min."; + else + document.getElementById("rate-reset").innerHTML = "Resets in: " + Math.round(data.account.rate.reset / 60 / 60) + " hr."; + + document.getElementById("join-link").innerHTML = 'My Account'; + document.getElementById("join-link").setAttribute('href','https://mailhops.com/account/'+api_key); + + } else if (xmlhttp.status === 401) { + self.planError("That API key could not be found."); + } + else if (!!data.error) { + self.planError(xmlhttp.status+': '+data.error.message); + } + mailHopPreferences.savePreferences(); + } catch (e){ + self.planError('Connection Failed to\n '+e+'!'); + } + } + }; + xmlhttp.send(null); + } else { + this.planError('Enter a valid API key above.'); + } + } + + }; + +mailHopPreferences.loadPreferences(); \ No newline at end of file diff --git a/chrome/content/mailhops-1-utils.js b/js/utils.js similarity index 82% rename from chrome/content/mailhops-1-utils.js rename to js/utils.js index a2302c5..7638420 100644 --- a/chrome/content/mailhops-1-utils.js +++ b/js/utils.js @@ -1,4 +1,4 @@ -var mailHopsUtils = { +const MailHopsUtils = { countries: ["ad","ae","af","ag","ai","al","am","an","ao","ar","as","at","au","aw","ax","az","ba","bb","bd","be","bf","bg","bh","bi","bj","bm","bn","bo","br","bs","bt","bv","bw","by","bz","ca","catalonia","cc","cd","cf","cg","ch","ci","ck","cl","cm","cn","co","cr","cs","cu","cv","cx","cy","cz","de","dj","dk","dm","do","dz","ec","ee","eg","eh","england","er","es","et","europeanunion","fam","fi","fj","fk","fm","fo","fr","ga","gb","gd","ge","gf","gh","gi","gl","gm","gn","gp","gq","gr","gs","gt","gu","gw","gy","hk","hm","hn","hr","ht","hu","id","ie","il","in","io","iq","ir","is","it","jm","jo","jp","ke","kg","kh","ki","km","kn","kp","kr","kw","ky","kz","la","lb","lc","li","lk","lr","ls","lt","lu","lv","ly","ma","mc","md","me","mg","mh","mk","ml","mm","mn","mo","mp","mq","mr","ms","mt","mu","mv","mw","mx","my","mz","na","nc","ne","nf","ng","ni","nl","no","np","nr","nu","nz","om","pa","pe","pf","pg","ph","pk","pl","pm","pn","pr","ps","pt","pw","py","qa","re","ro","rs","ru","rw","sa","sb","sc","scotland","sd","se","sg","sh","si","sj","sk","sl","sm","sn","so","sr","st","sv","sy","sz","tc","td","tf","tg","th","tj","tk","tl","tm","tn","to","tr","tt","tv","tw","tz","ua","ug","um","us","uy","uz","va","vc","ve","vg","vi","vn","vu","wales","wf","ws","ye","yt","za","zm","zw"], @@ -110,36 +110,12 @@ addCommas: function(nStr){ return x1 + x2; }, -launchExternalURL: function(url){ - var messenger = Components.classes["@mozilla.org/messenger;1"].createInstance().QueryInterface(Components.interfaces.nsIMessenger); - messenger.launchExternalURL(url); -}, - -launchWhoIs: function(ip){ - this.launchExternalURL('https://www.mailhops.com/whois/' + ip); -}, - launchSpamHausURL: function(ip){ this.launchExternalURL('http://www.spamhaus.org/query/bl?ip=' + ip); }, -launchMap: function(route,options){ - - if(route != ''){ - var lookupURL=this.getAPIUrl(options)+'/map/?'+this.getAPIUrlParams(options)+'&l='+options.lan+'&u='+options.unit+'&r='+String(route); - - if(options.fkey != '') - lookupURL += '&fkey='+options.fkey; - - if(options.map_provider) - lookupURL += '&mp='+options.map_provider; - - window.openDialog("chrome://mailhops/content/mailhopsMap.xul","MailHops",'toolbar=no,location=no,directories=no,menubar=yes,scrollbars=yes,close=yes,width=1024,height=768,resizable=yes', {src: lookupURL}); - } -}, - -getAPIUrl: function(options){ - return options.api_http+options.api_host+'/v2'; +getAPIUrl: function(){ + return 'https://api.mailhops.com/v2'; }, getAPIUrlParams: function(options){ @@ -178,14 +154,14 @@ getWeatherIcon: function(icon){ }, getDistance: function(from, to, unit) { - if(!from || !to || !from['lat'] || !to['lat']) + if(!from || !to || !from.coords) return 0; - var lat = parseFloat(from['lat']); - var lon1 = parseFloat(from['lng']); - var lat2 = parseFloat(to['lat']); - var lon2 = parseFloat(to['lng']); - unit = unit || 'mi';//mi or km + var lat = parseFloat(from.coords[1]); + var lon1 = parseFloat(from.coords[0]); + var lat2 = parseFloat(to.coords[1]); + var lon2 = parseFloat(to.coords[0]); + unit = unit || 'mi'; //mi or km lat *= (Math.PI/180); lon1 *= (Math.PI/180); @@ -197,17 +173,24 @@ getDistance: function(from, to, unit) { if (unit == 'mi') { dist = (dist / 1.609344); } - return dist; + return this.addCommas(Math.round(dist)); }, - - getOriginatingCountryCode: function(route) { + getSender: function(route) { if(route && route.length){ - for(var r=0; r
+ + + + + + +