1/* This Source Code Form is subject to the terms of the Mozilla Public 2 * License, v. 2.0. If a copy of the MPL was not distributed with this file, 3 * You can obtain one at http://mozilla.org/MPL/2.0/. */ 4 5const { XPCOMUtils } = ChromeUtils.import( 6 "resource://gre/modules/XPCOMUtils.jsm" 7); 8const { Services } = ChromeUtils.import("resource://gre/modules/Services.jsm"); 9 10XPCOMUtils.defineLazyServiceGetter( 11 this, 12 "IDNService", 13 "@mozilla.org/network/idn-service;1", 14 "nsIIDNService" 15); 16 17XPCOMUtils.defineLazyGlobalGetters(this, ["URL"]); 18 19/** 20 * Properly convert internationalized domain names. 21 * @param {string} host Domain hostname. 22 * @returns {string} Hostname suitable to be displayed. 23 */ 24function handleIDNHost(hostname) { 25 try { 26 return IDNService.convertToDisplayIDN(hostname, {}); 27 } catch (e) { 28 // If something goes wrong (e.g. host is an IP address) just fail back 29 // to the full domain. 30 return hostname; 31 } 32} 33 34/** 35 * Get the effective top level domain of a host. 36 * @param {string} host The host to be analyzed. 37 * @return {str} The suffix or empty string if there's no suffix. 38 */ 39function getETLD(host) { 40 try { 41 return Services.eTLD.getPublicSuffixFromHost(host); 42 } catch (err) { 43 return ""; 44 } 45} 46 47/** 48 * shortURL - Creates a short version of a link's url, used for display purposes 49 * e.g. {url: http://www.foosite.com} => "foosite" 50 * 51 * @param {obj} link A link object 52 * {str} link.url (required)- The url of the link 53 * @return {str} A short url 54 */ 55function shortURL({ url }) { 56 if (!url) { 57 return ""; 58 } 59 60 // Make sure we have a valid / parseable url 61 let parsed; 62 try { 63 parsed = new URL(url); 64 } catch (ex) { 65 // Not entirely sure what we have, but just give it back 66 return url; 67 } 68 69 // Clean up the url (lowercase hostname via URL and remove www.) 70 const hostname = parsed.hostname.replace(/^www\./i, ""); 71 72 // Remove the eTLD (e.g., com, net) and the preceding period from the hostname 73 const eTLD = getETLD(hostname); 74 const eTLDExtra = eTLD.length ? -(eTLD.length + 1) : Infinity; 75 76 // Ideally get the short eTLD-less host but fall back to longer url parts 77 return ( 78 handleIDNHost(hostname.slice(0, eTLDExtra) || hostname) || 79 parsed.pathname || 80 parsed.href 81 ); 82} 83 84const EXPORTED_SYMBOLS = ["shortURL", "getETLD"]; 85