home *** CD-ROM | disk | FTP | other *** search
Wrap
Text File | 2010-04-16 | 170.7 KB | 5,533 lines
const Cc = Components.classes; const Ci = Components.interfaces; const Cr = Components.results; const Cu = Components.utils; const EXT_ID = "yasearch@yandex.ru"; const CHROME_IMAGES = "chrome://yasearch/skin/images/"; const CHROME_CONTENT = "chrome://yasearch/content/"; Cu.import("resource://gre/modules/XPCOMUtils.jsm"); /** ================================================================================ **/ ["consts", "utils", "cache_wrapper", "ya_storage", "ya_installer", "ya_defence", "ya_bookmarks", "ya_overlay", "ya_city", "ya_searchplugin", "ya_uservices", "ya_partner", "ya_sshot", "ya_ftab"] .forEach( function(aScriptName) { this.loadSubScript(CHROME_CONTENT + "sub-scripts/" + aScriptName + ".js"); }, Cc["@mozilla.org/moz/jssubscript-loader;1"].getService(Ci.mozIJSSubScriptLoader) ); /** ================================================================================ **/ function nsIYaSearch() { this.version = "201001200600"; this.versionBuild = "7394"; this.VERSION_BUILD = ""; this.wrappedJSObject = this; this.debug = false; this._inited = false; this.EXT_ID = EXT_ID; this.prefs = { _showBloggersValuePrefName: "yasearch.general.ui.show.bloggers.value", get showBloggersValue() { return gYaSearchService.getBoolPref(this._showBloggersValuePrefName); }, set showBloggersValue(val) { gYaSearchService.setBoolPref(this._showBloggersValuePrefName, !!val); return this.showBloggersValue; }, _showCyValuePrefName: "yasearch.general.ui.show.cy.value", get showCyValue() { return gYaSearchService.getBoolPref(this._showCyValuePrefName); }, set showCyValue(val) { gYaSearchService.setBoolPref(this._showCyValuePrefName, !!val); return this.showCyValue; }, _highlighterEnabledPrefName: "yasearch.general.ui.highlighter.enabled", get highlighterEnabled() { return gYaSearchService.getBoolPref(this._highlighterEnabledPrefName); }, set highlighterEnabled(val) { gYaSearchService.setBoolPref(this._highlighterEnabledPrefName, !!val); return this.highlighterEnabled; }, _showSiteSearchPrefName: "yasearch.general.ui.show.site.search", get showSiteSearch() { return gYaSearchService.getBoolPref(this._showSiteSearchPrefName); }, set showSiteSearch(val) { gYaSearchService.setBoolPref(this._showSiteSearchPrefName, !!val); return this.showSiteSearch; }, _searchHistoryEnabledPrefName: "yasearch.general.ui.search.history.enabled", get searchHistoryEnabled() { return gYaSearchService.getBoolPref(this._searchHistoryEnabledPrefName); }, set searchHistoryEnabled(val) { gYaSearchService.setBoolPref(this._searchHistoryEnabledPrefName, !!val); return this.searchHistoryEnabled; }, _commandOpenTabPrefName: "yasearch.general.ui.command.open.tab", get commandOpenTab() { return gYaSearchService.getBoolPref(this._commandOpenTabPrefName); }, _showCityLabel: "yasearch.general.ui.show.city.label", get showCityLabel() { return gYaSearchService.getBoolPref(this._showCityLabel); }, set showCityLabel(val) { gYaSearchService.setBoolPref(this._showCityLabel, !!val); return this.showCityLabel; } }; this.updateTimer = { "_Login": null, "_Guid": null, "_GuidRefresh": null, "_MailAndFeeds": null, "_Bookmarks": null }; this.checkTimeOut = { "_Login": 5 * MIN_SEC, "_Guid": DAY_SECS, "_GuidRefresh": 3600010, "_MailAndFeeds": 0, "_Bookmarks": DAY_SECS }; this.feedsCounter = 0; this._runnedNotifications = []; this.usersData = {}; this.maxUnreadInXML = 30; this.showLocalWelcomePage = false; this.checkKeywordURL = null; } nsIYaSearch.prototype = { QueryInterface: XPCOMUtils.generateQI([Ci.nsISupports, Ci.nsIYaSearch, Ci.nsIObserver, Ci.nsISupportsWeakReference]), ASSERT: function() {}, log: function(msg) { if (!this.debug) return; var date = new Date(); var time = [date.getHours(), date.getMinutes(), date.getSeconds()].join(":") + "." + date.getMilliseconds(); msg = "[nsIYaSearch (" + time + ")]: " + msg + "\n"; CONSOLE_SERVICE.logStringMessage(msg); //this.tmpLogOutput.write(msg, msg.length); }, get tmpLogOutput() { if (!this.__tmpLogOutput) { var tmpFile = Cc["@mozilla.org/file/directory_service;1"].getService(Ci.nsIProperties).get("TmpD", Ci.nsIFile); tmpFile.append("!!_ya_searchlog_"); var os = Cc["@mozilla.org/network/file-output-stream;1"].createInstance(Ci.nsIFileOutputStream); os.init(tmpFile, 0x02 | 0x08 | 0x20, 0755, 0); this.__tmpLogOutput = os; } return this.__tmpLogOutput; }, isLogin: false, cookieManager: Cc["@mozilla.org/cookiemanager;1"].getService(Ci.nsICookieManager), defaultSearchEngineId: "www", settingsFolderName: "yandex", xmlServicesFileName: "services.data.xml", xmlServicesFile: null, xmlServices: null, contentDir: null, _xsltemplates: {}, xsltImportRegExp: new RegExp(/<xsl:import href="chrome:\/\/yasearch\/content\/xsl\-templ\/xsl\-(.*)\.xsl"\/>/), domParser: Cc["@mozilla.org/xmlextras/domparser;1"].getService(Ci.nsIDOMParser), xmlSerializer: Cc["@mozilla.org/xmlextras/xmlserializer;1"].getService(Ci.nsIDOMSerializer), xPathEvaluator: Cc["@mozilla.org/dom/xpath-evaluator;1"].getService(Ci.nsIDOMXPathEvaluator), unSnapshotType: Ci.nsIDOMXPathResult.UNORDERED_NODE_SNAPSHOT_TYPE, orSnapshotType: Ci.nsIDOMXPathResult.ORDERED_NODE_SNAPSHOT_TYPE, soundService: Cc["@mozilla.org/sound;1"].createInstance(Ci.nsISound), windowMediator: Cc["@mozilla.org/appshell/window-mediator;1"].getService(Ci.nsIWindowMediator), windowWatcher: Cc["@mozilla.org/embedcomp/window-watcher;1"].getService(Ci.nsIWindowWatcher), promptService: Cc["@mozilla.org/embedcomp/prompt-service;1"].getService(Ci.nsIPromptService), /**--------------------------------------------------------------------------------------------------**/ _getHostURIFromURL: function(aURL) { var host = aURL.replace(/^\s*([-\w]*:\/+)?/, ""); return this.makeURI("http://" + host); }, isCookiesAllowedForHost: function(aURL) { var res = null; var uri = this._getHostURIFromURL(aURL); if (!uri) return res; var permissionManager = Cc["@mozilla.org/permissionmanager;1"].getService(Ci.nsIPermissionManager); switch (permissionManager.testPermission(uri, "cookie")) { case permissionManager.ALLOW_ACTION: res = true; break; case permissionManager.DENY_ACTION: res = null; break; case permissionManager.UNKNOWN_ACTION: default: var cookieBehaviorValue = this.getIntPref("network.cookie.cookieBehavior"); res = (cookieBehaviorValue === 0); break; } return res; }, allowCookiesForHost: function(aURL) { if (this.isCookiesAllowedForHost(aURL)) return true; var uri = this._getHostURIFromURL(aURL); if (uri) { var permissionManager = Cc["@mozilla.org/permissionmanager;1"].getService(Ci.nsIPermissionManager); permissionManager.add(uri, "cookie", permissionManager.ALLOW_ACTION); } return this.isCookiesAllowedForHost(aURL); }, setSessionFromCookies: function(aCheckExpired) { if (!this.isLogin && !this.loginProcessData.username) { var loginCookieValue = this.getYandexCookie("yandex_login", aCheckExpired); var sessionCookieValue = this.getYandexCookie("Session_id", aCheckExpired); if (loginCookieValue && sessionCookieValue) { this.session = {name: "Id", val: sessionCookieValue}; this.session = {name: "Login", val: loginCookieValue}; return true; } } return false; }, checkAuthOnStart: function(aSkipGettingStaticData) { if ((typeof aSkipGettingStaticData === "undefined") && !this.yaRootDomain) return this.getAuthStaticData(this.checkAuthOnStart.bind(this)); if (this.yaRootDomain && !this.isLogin && !this.loginProcessData.username) this.setSessionFromCookies(true); }, getAuthStaticData: function(aCallback) { this.xmlHttpRequest("https://passport.yandex.ru/bar.txt?" + getNCRndStr(), { callbackFunc: this.getAuthStaticDataCallback.bind(this, aCallback) }); }, getAuthStaticDataCallback: function(aReq, aCallback) { var res = false; if (!this.isReqError(aReq)) { var staticDataArray = aReq.target.responseText.split(/\r?\n/); var rootPass = false; var resArray = []; for (var i = 0, len = staticDataArray.length; i < len; i++) { var item = staticDataArray[i].split("#")[0]; if (/^\/:/.test(item)) { if (!rootPass) rootPass = item; } else if (item.indexOf(":") > 0) { resArray.push(item); } } if (rootPass) { resArray.unshift(G_TIME_NOW, rootPass); this.yaAuthStaticData = resArray.join("~~~"); } res = !!this.yaRootDomain; } if (aCallback) aCallback(res); }, __yaAuthStaticData: null, set yaAuthStaticData(aVal) { this.setCharPref("yasearch.auth.static", aVal); this.__yaAuthStaticData = null; return aVal; }, get yaAuthStaticData() { if (this.__yaAuthStaticData === null) { var staticData = { ts: 0, get needRefresh() { var timeNow = G_TIME_NOW; return ((timeNow - this.ts > 1 * DAY_SECS) || this.ts > timeNow) ? true : false; }, rootDomain: false, rootPass: false, rootPasslogin: false, rootPasslogout: false, allHostsRegExp: false, hosts: {} }; var data = (this.getCharPref("yasearch.auth.static") || "").split("~~~"); if (data.length > 1 && /^\d+$/.test(data[0])) { var lastTime = +data[0]; try { var hostStr = data[1]; var uri = hostStr && /^\/:/.test(hostStr) ? this.makeURI(hostStr.replace(/^\/:/,"")) : null; } catch(e){} if (uri && /https?/.test(uri.scheme)) { var allHostsRegExp = []; staticData.ts = lastTime; var passUrl = uri.spec; staticData.rootPass = passUrl; passUrl += (/\/$/.test(passUrl) ? "" : "/") + "xml/log"; staticData.rootPasslogin = passUrl + "in"; staticData.rootPasslogout = passUrl + "out"; var domainArr = uri.host.split(".").reverse(); staticData.rootDomain = domainArr.length > 1 ? ("." + domainArr[1] + "." + domainArr[0]) : false; var i = 2, cookies = data[i]; while (cookies) { var hostIndx = cookies.indexOf(":"); if (hostIndx > 2) { var host = cookies.substring(0, hostIndx); var hostReg = host.replace(/(\-|\.)/g,"\\\$1").replace(/^(\*\\\.)/,"(.*\\.)?"); allHostsRegExp.push(hostReg); hostReg = new RegExp("^" + hostReg + "$", "i"); var cookiesArr = []; for each (var cook in cookies.substring(++hostIndx).split(",")) if (cook > "") cookiesArr.push(cook); if (cookiesArr.length) staticData.hosts[host] = {cookies: cookiesArr, hostReg: hostReg}; } cookies = data[++i]; } if (allHostsRegExp.length) staticData.allHostsRegExp = new RegExp("^(" + allHostsRegExp.join("|") + ")$", "i"); } } this.__yaAuthStaticData = staticData; } return this.__yaAuthStaticData; }, get yaRootDomain() { return this.yaAuthStaticData.rootDomain; }, getYandexCookie: function(aName, aCheckExpired) { let rootDomain = this.yaRootDomain; if (rootDomain) { const nsICookie = Ci.nsICookie; let timeNow = parseInt(G_TIME_NOW / 1000, 10); let cookEnum = this.cookieManager.enumerator; while (cookEnum.hasMoreElements()) { let cookie = cookEnum.getNext(); if (cookie && cookie instanceof nsICookie && cookie.host == rootDomain && cookie.name == aName && cookie.path == "/" && cookie.value.toString() != "" && (aCheckExpired ? timeNow < cookie.expires : true)) { let res = cookie.value.toString(); return aName == "Session_id" ? this.checkSessionCookieValue(res) : res; } } } return false; }, checkSessionCookieValue: function(aValue) { return (aValue && aValue.length) ? aValue : false; }, getBrowserHostCookies: function(aOnlyYandexList) { var res = {}; var allHostsRegExp = aOnlyYandexList ? this.yaAuthStaticData.allHostsRegExp : false; if (!aOnlyYandexList || allHostsRegExp) { const nsICookie = Ci.nsICookie; var cookEnum = this.cookieManager.enumerator; while (cookEnum.hasMoreElements()) { var cookie = cookEnum.getNext(); if (cookie && cookie instanceof nsICookie) { var host = cookie.host; if (!aOnlyYandexList || allHostsRegExp.test(host)) { var newCookie = {}; for each (var prop in ["name", "value", "host", "path", "expires"]) newCookie[prop] = cookie[prop]; if (!res[host]) res[host] = []; res[host].push(newCookie); } } else { break; } } } return res; }, getAuthDinamicData: function(aType) { let url = this.yaAuthStaticData["rootPass" + aType]; if (url) { url = this.appendStatData2Url(url + "?" + getNCRndStr(), {}); return this.xmlHttpRequest(url, {callbackFunc: this.getAuthDinamicDataCallback.bind(this, aType)}); } }, getAuthDinamicDataCallback: function(aReq, aType) { var res = false; if ((aType === "logout" && !this.isLogin) || (aType === "login" && this.isLogin)) res = this.manageCookies(this.isReqError(aReq) ? false : aReq.target.responseText.replace(/<\?xml .+\?>[\r\n]*/,""), aType); }, manageCookies: function(aXmlString, aType) { var res = false; var presentHosts; var cookieManager = this.cookieManager; var cookiesXml = this.safeE4Xml(aXmlString, "<mda/>", "mda"); if (cookiesXml.domain.length()) { var cookieService = Cc["@mozilla.org/cookieService;1"].getService().QueryInterface(Ci.nsICookieService); presentHosts = this.getBrowserHostCookies(); var timeNow = G_TIME_NOW; var timeNowSec = parseInt(timeNow / 1000, 10); for (var i = 0, len_i = cookiesXml.domain.length(); i < len_i; i++) {//for each not work in some versions var domain = cookiesXml.domain[i]; var domainId = domain.@id.toString(); for each (var actionTag in domain.*) { var action = actionTag.name().toString(); for (var j = 0, len_j = actionTag.cookie.length(); j < len_j; j++) { var cookie = actionTag.cookie[j]; var cookieName = cookie.@id.toString(); if (cookieName > "") { var cookiePath = cookie.@path.toString() == "" ? "/" : cookie.@path.toString(); switch (action) { case "remove": cookieManager.remove(domainId, cookieName, cookiePath, false); break; case "set": var maxAge = +(cookie["@max-age"].toString()); if (cookie.@override.toString() != "yes" && presentHosts[domainId]) { for each (var existCookie in presentHosts[domainId]) { if (existCookie.name === cookieName) { if ((existCookie.expires == 0 && maxAge == 0) || (existCookie.expires > 0 && maxAge > 0 && timeNowSec < existCookie.expires)) cookieName = false; break; } } } if (cookieName) { var uri = Cc["@mozilla.org/network/standard-url;1"].createInstance(Ci.nsIURI); uri.spec = "http://" + domainId; var cookieStr = "" + cookieName + "=" + cookie.text().toString() + ";"; if (domainId.charAt(0) == ".") cookieStr += "domain=" + domainId + ";"; cookieStr += "path=" + cookiePath + ";"; if (maxAge > 0) cookieStr += "expires=" + (new Date(timeNow + maxAge*1000).toGMTString()) + ";" cookieService.setCookieString(uri, null, cookieStr, null); } break; default: break; } } } } } res = true; } else if (aType == "logout") { presentHosts = this.getBrowserHostCookies(true); for each (var staticHost in this.yaAuthStaticData.hosts) { for (var presentHost in presentHosts) { if (staticHost.hostReg.test(presentHost)) { var presentCookies = presentHosts[presentHost]; for each (var staticName in staticHost.cookies) { var i = presentCookies.length; while (--i > -1) { var presentCookie = presentCookies[i]; if (staticName == presentCookie.name) { cookieManager.remove(presentCookie.host, presentCookie.name, presentCookie.path, false); presentCookies.splice(i,1); } } } } } } res = true; } return res; }, /**--------------------------------------------------------------------------------------------------**/ isFirstDOMWinStuffDone: false, onBrowserUIStartupComplete: function() { if (!this._inited || this.isFirstDOMWinStuffDone) return; this.stringBundle = null;//refresh non-ru-locale strbundle this.isFirstDOMWinStuffDone = true; if (this.checkKeywordURL) { if (this.checkKeywordURL === "set") { this._setKeywordUrl(true); } else if (this.checkKeywordURL === "check") { this._checkKeywordUrl(); } this.checkKeywordURL = null; } if (typeof(gYaSearchPlugin) === "object" && "checkSearchPluginInstall" in gYaSearchPlugin) gYaSearchPlugin.checkSearchPluginInstall(); }, onSessionstoreWindowsRestored: function() { if (!this._inited) return; if (this.showLocalWelcomePage) { this.showLocalWelcomePage = false; new G_Timer(function(){ gYaSearchService.loadURI("chrome://yasearch/locale/first-start/welcome.html", "tab"); }, 500); } if (this.isLogin && this.isCountersAutoUpdateEnabled) this.refreshHTTPData("mailAndFeeds"); }, /**--------------------------------------------------------------------------------------------------**/ init: function() { this.debug = this.getBoolPref("yasearch.general.debug.enabled"); if (!this.getBoolPref("yasearch.license.accepted")) { if (!this.getBoolPref("yasearch.license.show")) { this.setBoolPref("yasearch.license.accepted", true); } else { try { let setupWin = this.windowWatcher.openWindow(null, "chrome://yasearch/content/first-start/wizard.xul", null, "centerscreen,modal", null); if (!this.getBoolPref("yasearch.license.accepted")) { let refuseWin = this.windowWatcher.openWindow(null, "chrome://yasearch/content/first-start/license-refuse.xul", null, "centerscreen,modal", null); Cc["@mozilla.org/extensions/manager;1"].getService(Ci.nsIExtensionManager).disableItem(EXT_ID); return;//this._inited = false; } } catch(e) { this.log(e); return; } } this.resetPref("yasearch.license.hidden"); // persist accepted pref: don't show dialog if fx crash try { let prefService = Cc["@mozilla.org/preferences-service;1"].getService(Ci.nsIPrefService); prefService.savePrefFile(null); } catch(e) { this.log(e); } } this._inited = true; ["cookie-changed", "http-on-modify-request", "http-on-examine-response"] .forEach(function(aTopicName) { OBSERVER_SERVICE.addObserver(this, aTopicName, true); }, this); if (typeof(gYaStorage) === "object" && "init" in gYaStorage) gYaStorage.init(); if (typeof(gYaInstaller) === "object" && "init" in gYaInstaller) gYaInstaller.init(); if (typeof(gYaOverlay) === "object" && "init" in gYaOverlay) gYaOverlay.init(); if (null === this.getBoolPref("yasearch.mail.ui.notification.enabled")) { let showNotificationsByDefault = !this.isYaOnlineInstalled; this.setBoolPref("yasearch.mail.ui.notification.enabled", showNotificationsByDefault); this.setBoolPref("yasearch.feeds.ui.notification.enabled", showNotificationsByDefault); } this.checkTimeOut._MailAndFeeds = this.isCountersAutoUpdateEnabled ? (this.getIntPref("yasearch.http.update.interval") * MIN_SEC || 0) : 0; this.appendUserSessionData("data"); this.checkAuthOnStart(); this.hackKnownSkins(); }, get buttonsInfo() { let enumerator = this.windowMediator.getEnumerator("navigator:browser"); if (enumerator.hasMoreElements()) { try { let browser = enumerator.getNext(); return browser.Ya.buttonsObject; } catch(e) {} } return null; }, loginProcessData: {}, initLoginProcess: function(aName, aPassword, aTwoWeeks, aManualLogin) { if (!aName || !aPassword) return false; this.loginState = this.LOGIN_STATES.REQUEST; this.loginProcessData = { username: aName, password: aPassword, twoWeeks: aTwoWeeks, manualLogin: aManualLogin }; if (!this.yaRootDomain) this.getAuthStaticData(this.__initLoginProcess.bind(this)); else this.__initLoginProcess(); }, __initLoginProcess: function() { if (!this.yaRootDomain) this.loginState = this.LOGIN_STATES.NET_ERROR; else this.startLoginConnection(); }, LOGIN_STATES: { NO_AUTH: 0, ERROR: 1, CAPTCHA_ERROR: 2, NET_ERROR: 3, REQUEST: 4, AUTH: 5 }, _loginState: 0, get loginState() { return this._loginState; }, set loginState(val) { let newLoginStateValue = parseInt(val, 10); if (this._loginState !== newLoginStateValue) { if (newLoginStateValue < this.LOGIN_STATES.NO_AUTH || newLoginStateValue > this.LOGIN_STATES.AUTH) { this.log("loginState: bad value (" + val + ")"); return this._loginState; } this._loginState = newLoginStateValue; OBSERVER_SERVICE.notifyObservers(null, "Ya-Login-State-Changed", false); switch (newLoginStateValue) { case this.LOGIN_STATES.AUTH: case this.LOGIN_STATES.NO_AUTH: OBSERVER_SERVICE.notifyObservers(null, "Ya-Refresh-Login-Status", false); break; default: break; } } return this._loginState; }, talkToServer: function (aURL, aPostData, aCookieData, aReferrer, aCallbackFunc) { var uri = this.makeURI(aURL); var uploadStream = Cc["@mozilla.org/io/string-input-stream;1"].createInstance(Ci.nsIStringInputStream); if (aPostData) uploadStream.setData(aPostData, aPostData.length); var channel = IO_SERVICE.newChannelFromURI(uri); this._loginChannel = channel; var httpChannel = channel.QueryInterface(Ci.nsIHttpChannel); if (aReferrer) { var referrerUri = this.makeURI(aReferrer); httpChannel.referrer = referrerUri; } if (aPostData) { var uploadChannel = channel.QueryInterface(Ci.nsIUploadChannel); uploadChannel.setUploadStream(uploadStream, "application/x-www-form-urlencoded", -1); httpChannel.requestMethod = "POST"; } if (aCookieData) for (var run = 0; run < aCookieData.length; run++) httpChannel.setRequestHeader("Cookie", aCookieData[run], true); var observer = new this.observer(aCallbackFunc); channel.notificationCallbacks = observer; channel.asyncOpen(observer, null); }, observer: function(aCallbackFunc) { return ({ data: "", onStartRequest: function (aRequest, aContext) { this.data = ""; }, onDataAvailable: function (aRequest, aContext, aStream, aSourceOffset, aLength) { var scriptableInputStream = Cc["@mozilla.org/scriptableinputstream;1"].createInstance(Ci.nsIScriptableInputStream); scriptableInputStream.init(aStream); this.data += scriptableInputStream.read(aLength); }, onStopRequest: function (aRequest, aContext, aStatus) { aCallbackFunc({"data": this.data, "request": aRequest}); }, onStatus: function(aRequest, aContext, aStatus, aStatusArg) {}, onProgress: function(aRequest, aContext, aProgress, aProgressMax) {}, onChannelRedirect: function (aOldChannel, aNewChannel, aFlags) {}, onRedirect : function (aOldChannel, aNewChannel) {}, getAuthPrompt: function(aPromptReason, iid) { var ww = Cc["@mozilla.org/embedcomp/window-watcher;1"].getService(Ci.nsIWindowWatcher); return ww.getNewAuthPrompter(null); }, interfaces: [ Ci.nsISupports, Ci.nsIStreamListener, Ci.nsISupportsWeakReference, Ci.nsIPrompt, Ci.nsIAuthPrompt, Ci.nsIAuthPromptProvider, Ci.nsIProgressEventSink, Ci.nsIInterfaceRequestor, Ci.nsIChannelEventSink, Ci.nsIHttpEventSink, Ci.nsIWebProgress ], QueryInterface: function(iid) { if (!this.interfaces.some( function(v) { return iid.equals(v) } )) throw Cr.NS_ERROR_NO_INTERFACE; if (iid.equals(Ci.nsIPrompt)) { var prompt = Cc["@mozilla.org/network/default-prompt;1"].createInstance(); return prompt.QueryInterface(iid); } if (iid.equals(Ci.nsIAuthPrompt)) { var prompt = Cc["@mozilla.org/network/default-auth-prompt;1"].createInstance(); return prompt.QueryInterface(iid); } return this; }, getInterface: function(iid) { try { return this.QueryInterface(iid); } catch(e) { return null; } } }); }, _logoutRequest: null, cancelLogoutConnection: function() { if (this._logoutRequest && this._logoutRequest.channel && this._logoutRequest.channel.isPending()) this._logoutRequest.channel.cancel(Cr.NS_BINDING_ABORTED); this._logoutRequest = null; }, startLogoutConnection: function() { this.cancelLogoutConnection(); var url = "https://passport.yandex.ru/passport?mode=logout&target=bar" + "&yu=" + encodeURIComponent(this.getYandexCookie("yandexuid", false) || ""); this._logoutRequest = this.xmlHttpRequest(url, {callbackFunc: this.startLogoutConnectionCallback.bind(this)}); }, startLogoutConnectionCallback: function(aReq) { if (this.isReqError(aReq)) { this.manageCookies(false, "logout"); this.cancelLogoutConnection(); } else { this._logoutRequest = this.getAuthDinamicData("logout"); } }, startLoginConnection: function() { this.cancelLogoutConnection(); var data = "login=" + encodeURIComponent(this.loginProcessData.username) + "&passwd=" + encodeURIComponent(this.loginProcessData.password) + "&retpath=https%3A%2F%2Fpassport.yandex.ru%2Fpassport%3Fmode%3Dpassport%26target%3Dbar" + "×tamp=" + G_TIME_NOW; if (this.loginProcessData.twoWeeks) data += "&twoweeks=yes"; this._sessionId = false; this.talkToServer("https://passport.yandex.ru/passport?mode=auth&target=bar", data, null, "https://passport.yandex.ru/passport?mode=passport&target=bar", this.talkCallback.bind(this)); }, talkCallback: function(aData) { var aRequest = aData.request, status = null, warningText = ""; try { aRequest.QueryInterface(Ci.nsIHttpChannel); status = aRequest.responseStatus; warningText = aRequest.getResponseHeader("Warning"); } catch(e) {} if (!status || (status != 200 && status != 302)) { if (!this.loginProcessData.manualLogin) this.setTimer("_Login"); this.loginState = this.LOGIN_STATES.NET_ERROR; } else if (!this.isLogin) { this._loginFailCounter++; this.clearAllTimers(); if (/showcaptcha/.test(warningText)) { this._loginFailCounter += 3; this.loginState = this.LOGIN_STATES.CAPTCHA_ERROR; } else { this.loginState = this.LOGIN_STATES.ERROR; } this.loginProcessData = {}; //this.loginProcessData.manualLogin = false; } }, _loginFailCounter: 0, get loginFail() { return (this._loginFailCounter >= 3); }, _sessionId: false, _sessionLogin: false, set session(aData) { if (aData.name == "Id") aData.val = this.checkSessionCookieValue(aData.val); if (this.username && aData.name == "Login" && aData.val && aData.val.replace(/\./g, "-") !== this.username && this._sessionId) aData.val = false; this["_session" + aData.name] = aData.val; if (!aData.val) { this.fireAfterLogOut(); } else { if (this._sessionId && this._sessionLogin) this.fireAfterLogIn(); } }, get session() { return {id: this._sessionId, login: this._sessionLogin}; }, _username: false, get username() { return this._username; }, set username(val) { if (!val || val == "") val = false; this._username = val; if (val && "undefined" == typeof this.usersData[val]) this.usersData[val] = {}; return val; }, fireAfterLogIn: function() { if (this.isLogin) return; this._loginFailCounter = 0; this.isLogin = true; if (this._loginChannel) { this._loginChannel.cancel(true); this._loginChannel = null; } let loginProcessData = this.loginProcessData; if (loginProcessData.manualLogin) { this.passwordManager.storeLoginDetails(loginProcessData.username, loginProcessData.password, loginProcessData.twoWeeks); } this.username = this.session.login.replace(/\./g, "-"); this.clearAllTimers(); this.loginState = this.LOGIN_STATES.AUTH; if (this.isCountersAutoUpdateEnabled) this.refreshHTTPData("mailAndFeeds"); if (this.bookmarksIsOutOfDate) this.refreshHTTPData("bookmarks"); if (this.loginProcessData.username) this.getAuthDinamicData("login"); if (this.yaAuthStaticData.needRefresh) this.getAuthStaticData(); this.loginProcessData = {}; }, fireAfterLogOut: function(aClearCookies, aForgetLogin) { if (!this.isLogin) return; this.loginProcessData = {}; this.isLogin = false; if (aForgetLogin) this.passwordManager.removeUserData(this.username); if (aClearCookies) new G_Timer(function() { gYaSearchService.startLogoutConnection(); }, 0); this.username = false; this.session = { name: "Login", val: false }; this.clearAllTimers(); let enumerator = this.windowMediator.getEnumerator("Yasearch:AddDialog"); if (enumerator.hasMoreElements()) { while (enumerator.hasMoreElements()) enumerator.getNext().document.documentElement.cancelDialog(); } this.loginState = this.LOGIN_STATES.NO_AUTH; }, clearAllTimers: function() { this.clearTimer("_Login"); this.clearTimer("_MailAndFeeds"); this.clearTimer("_Bookmarks"); this.setNotifyTimer("cancel"); }, clearTimer: function(type) { if (type && this.updateTimer[type]) { this.updateTimer[type].cancel(); this.updateTimer[type] = null; } }, setTimer: function(type, aTimeout) { if (!type) throw "nsIYaSearch::setTimer -- no type"; aTimeout = aTimeout || this.checkTimeOut[type] || 0; if (this.updateTimer[type]) this.updateTimer[type].cancel(); else this.updateTimer[type] = Cc["@mozilla.org/timer;1"].createInstance(Ci.nsITimer); if (aTimeout > 0) this.updateTimer[type].initWithCallback(this[type], aTimeout, Ci.nsITimer.TYPE_ONE_SHOT); }, _Login: { notify: function(aTimer) { gYaSearchService.startLoginConnection(); } }, _MailAndFeeds: { notify: function(aTimer) { gYaSearchService.refreshHTTPData("mailAndFeeds"); } }, _Bookmarks: { notify: function(aTimer) { gYaSearchService.refreshHTTPData("bookmarks"); } }, _Guid: { notify: function(aTimer) { gYaSearchService.refreshHTTPData("guid"); } }, _GuidRefresh: { notify: function(aTimer) { gYaSearchService.clearTimer("_GuidRefresh"); } }, HTTPDataRequests: { _data: {}, add: function(aURL, aType, aRequest) { this._data[aURL] = { requestSimpleURL: aURL, request: aRequest, requestTime: G_TIME_NOW, isRequestPending: function() { return !!(this.request && this.request.channel.isPending()); }, cancelRequest: function() { this.request.channel.cancel(Cr.NS_BINDING_ABORTED); }, responseTime: 0, responseIsOK: null, types: {} } this._data[aURL].types[aType] = true; }, removeRequest: function(aRequest) { for each (var data in this._data) { if (data.request === aRequest) { data.request = null; return data; } } }, canResendRequest: function(aURL, aType) { if (aType == "allServices") return true; let data = this._data[aURL]; if (data) { let requestTimeDelta = Math.abs(G_TIME_NOW - data.requestTime); if (data.isRequestPending()) { if (requestTimeDelta > 30000) { data.cancelRequest(); return true; } data.types[aType] = true; return false; } let responseTimeDelta = Math.abs(G_TIME_NOW - data.responseTime); if (data.types[aType] && (requestTimeDelta < 1000 || (data.responseIsOK && responseTimeDelta < 5000))) return false; data.responseIsOK = null; data.responseTime = 0; } return true; }, processDataFromCache: function(aURL, aType, aData) { if (aData && aData.forceRequest) {// doom cached G_CacheWrapper.writeData(aURL, null); return false; } let lastDataFromCache = G_CacheWrapper.readData(aURL); if (lastDataFromCache) { gYaSearchService.processHTTPDataResponse(lastDataFromCache, aType, aData); return true; } return false; } }, manualRefreshHTTPData: function(aType, aData, aCallerElementId) { if (!aData) aData = {}; aData.manual = true; aData.callerElementId = aCallerElementId || ("yasearch-" + aType); this.refreshHTTPData(aType, aData); }, refreshHTTPData: function(aType, aData, aDelay) { if (!aData) aData = {}; //[2do] isAnyVisibleAuthElement new G_Timer( function() { gYaSearchService.__refreshHTTPData(aType, aData); }, aDelay || 10 ) }, __refreshHTTPData: function(aType, aData) { if (!aType || typeof(aType) != "string") throw "No type given in refreshHTTPData"; var url, appendTimestamp = false; aData.isCounters = false; switch (aType) { case "allServices": url = this.Counters.getURLForSID("allServices"); if (!url) return; aData.isCounters = true; appendTimestamp = true; break; case "mailAndFeeds": this.setTimer("_MailAndFeeds"); url = this.Counters.getURLForSID("allCounters"); if (!url) return; aData.isCounters = true; break; case "mail": case "lenta": case "money": case "fotki": case "yaru": case "moikrug": url = this.Counters.getURLForSID([aType]); if (!url) return; aData.isCounters = true; break; case "mailList": url = "http://mail.yandex.ru/api/barlist"; break; case "bookmarks": url = "http://zakladki.yandex.ru/bar/index.xml?newdescr=true"; appendTimestamp = true; break; case "city": this.setTimer(aData.timerName); if (this.yaCity.canRequestDataForCity(aData) == false) return; url = "http://export.yandex.ru/bar/reginfo.xml" + (aData.cityId == "" ? "" : "?region=" + aData.cityId); appendTimestamp = true; break; case "guid": url = this.generateGUIDStatusURL + this.generateGUIDData; break; default: break; } if (!url) throw new Error("Bad type given in refreshHTTPData"); switch (aType) { case "city": if (this.HTTPDataRequests.processDataFromCache(url, aType, aData)) { if (aData && aData.manual) { this.notifyBusyStateOfRequest(aType, true, true, aData.callerElementId); this.notifyBusyStateOfRequest(aType, false, true, aData.callerElementId); } return; } break; default: break; } this.notifyBusyStateOfRequest(aType, true, !!(aData && aData.manual), aData.callerElementId); if (this.HTTPDataRequests.canResendRequest(url, aType)) { var fullUrl = url; if (appendTimestamp) fullUrl += (/\?/.test(fullUrl) ? "&":"?") + "ts=" + G_TIME_NOW; if (!!(aData && aData.manual)) fullUrl = this.appendStatData2Url(fullUrl, {}); this.HTTPDataRequests.add(url, aType, this.xmlHttpRequest(fullUrl, {callbackFunc: this.refreshHTTPDataCallback.bind(this, aData)} )); } else { this.notifyBusyStateOfRequest(aType, false, !!(aData && aData.manual), aData.callerElementId); } }, refreshHTTPDataCallback: function(aReq, aData) { var data = this.HTTPDataRequests.removeRequest(aReq.target); if (!data) return; data.responseTime = G_TIME_NOW; var aType = data.types; if (!aType) throw new Error("No type given in refreshHTTPDataCallback"); var isCounters = aData.isCounters; if (this.isReqError(aReq)) { if ("guid" in aType) { this.clearTimer("_GuidRefresh"); } else { var nextTime = this.getIntPref("yasearch.http.update.weathertraff.interval") * MIN_SEC || 0; var fiveMin = 5 * MIN_SEC; if (!nextTime || nextTime > fiveMin) nextTime = fiveMin; if ("city" in aType) { this.setTimer("_CityItemTimer" + aData.cityId, nextTime); this.yaCity._setData(aData.cityId); } } data.responseIsOK = false; } else { G_DateUtils.updateServerTimeValue(aReq); var text = this.safeUnicode(aReq.target.responseText); if (!("guid" in aType)) this.checkNeedSendGuid(); var noAuthError = false; if (isCounters) { var countersError = this.Counters.getCounterError(text); if (countersError && countersError.type == "noauth") noAuthError = true; } if (noAuthError) { data.responseIsOK = false; this.fireAfterLogOut(); } else { data.responseIsOK = true; for (var typeStr in aType) this.processHTTPDataResponse(text, typeStr, aData); } } if (data.responseIsOK == false && ("allServices" in aType)) { this.Counters.setAllServicesError(true, true); } if (aData && aData.manual) { for (var typeStr in aType) this.notifyBusyStateOfRequest(typeStr, false, true, aData.callerElementId); } if ("city" in aType) G_CacheWrapper.writeData(data.requestSimpleURL, data.responseIsOK ? text : null); }, notifyBusyStateOfRequest: function(aType, aState, aIsManualRequest, aCallerElementId) { if (aIsManualRequest) OBSERVER_SERVICE.notifyObservers(null, "Ya-Refresh-Busy-State", aState + ":" + aCallerElementId); }, processHTTPDataResponse: function(aText, aTypeStr, aData) { var isManualRequest = !!(aData && aData.manual); switch (aTypeStr) { case "guid": this.timeGuid = true; OBSERVER_SERVICE.notifyObservers(null, "Ya-GUID-Response", "SENDED"); var msg = new XML(this.xmlSerializer.serializeToString(this.domParser.parseFromString(aText.replace(/<\?xml .+\?>[\r\n]*/,"").replace(/(<\/page>)[\r\n]*$/, '$1'), "text/xml"))); var showAlert = false, msgTime = msg.@time.toString(), version = msg.@version.toString(); var output = { title: msg.title.toString(), description: msg.description.toString(), icon: msg.icon.toString() }; if (version != "") { if (version > this.barExtensionVersion && Math.abs(this.guidUpdateDS - (G_TIME_NOW/DAY_SECS)) > 6) { msgTime = "error"; showAlert = true; } else if (msgTime != "" && msgTime != this.guidMessageTS && msg.addDescription.toString() != "") { output = { title: msg.addTitle.toString(), description: msg.addDescription.toString(), icon: msg.addIcon.toString() }; showAlert = true; } } else if (msgTime != "" && msgTime != this.guidMessageTS) { showAlert = true; } if (showAlert) this.showPermanentAlert(output.title, output.description, output.icon, msgTime); return; case "city": this.yaCity._setData(aData.cityId, aText.replace(/<\?xml .+\?>[\r\n]*/, ""), true); return; case "bookmarks": var bookmarksResponse = this.yaBookmarks.getServerResponse(aText); if (!bookmarksResponse.error) this.bookmarksDOMMenu = bookmarksResponse.xml; break; case "allServices": this.Counters.setDataFromJS(aText); case "mailAndFeeds": if (this.Counters.error) { if (aTypeStr == "mailAndFeeds") this.setTimer("_MailAndFeeds", this.Counters.errorTimeout); this.Counters.handleError(); } case "yaru": this.Counters.setDataFromInbox("yaru", aText); if (aTypeStr == "yaru") break; case "fotki": this.Counters.setDataFromInbox("fotki", aText); if (aTypeStr == "fotki") break; case "money": this.Counters.setDataFromInbox("money", aText); if (aTypeStr == "money") break; case "lenta": this.Counters.setDataFromInbox("lenta", aText); if (aTypeStr == "lenta") break; case "moikrug": this.Counters.setDataFromInbox("moikrug", aText); if (aTypeStr == "moikrug") break; case "mail": this.Counters.setDataFromInbox("mail", aText); var mCount = this.Counters.getCount("mail"); if (mCount && (mCount != this.mailCounter || (mCount > 0 && this.mailLastCheckIsOutOfDate))) { this.mailCounter = mCount; this.refreshHTTPData("mailList", aData); } else if (!mCount && mCount != this.mailCounter) { this.mailCounter = mCount; this.mailDOMMenuDoc = false; OBSERVER_SERVICE.notifyObservers(null, "Ya-Refresh-Data", "mailList"); } break; case "mailList": this.mailLastCheckIsOutOfDate = false; var doc = null; try { doc = this.domParser.parseFromString(aText, "text/xml"); if (!(doc instanceof Ci.nsIDOMDocument) || !(doc.firstChild.localName == "yandexmenu" || doc.firstChild.localName == "auther")) doc = null; } catch(e) {} if (!doc) break; var authError = this.xPathEvaluator.evaluate("count(//error[@reason='not authenticated'])", doc, null, Ci.nsIDOMXPathResult.NUMBER_TYPE, null); if (authError.numberValue) { this.fireAfterLogOut(); return; } var items = this.xPathEvaluator.evaluate("//item/item", doc, null, this.orSnapshotType, null); var newMailCounter = 0, newMailLastMaxId = this.mailLastMaxId, newLastItem; var itemsLength = items.snapshotLength; if (itemsLength > 0 && itemsLength < this.maxUnreadInXML) this.mailCounter = itemsLength; var mailMessageURLPrefix = "http://" + this.getLocaleDependedUrl("MailHost") + "/message?ids="; var increaseNewMailCounter = true; for (var i = 0; i < itemsLength; i++) { let item = items.snapshotItem(i); let id = /\?mesid=(\d+)/.exec(item.getAttribute("url"))[1]; item.setAttribute("url", mailMessageURLPrefix + id); if (!increaseNewMailCounter) continue; if (i == 0) this.mailLastMaxId = id; if (id > newMailLastMaxId) { newMailCounter++; newLastItem = newLastItem || item; } else { increaseNewMailCounter = false; } } this.mailDOMMenuDoc = doc; if (newMailCounter > 0) { if (newMailCounter == this.maxUnreadInXML) { let tmp = this.mailCounter - this.mailPermCounter; newMailCounter = tmp >= this.maxUnreadInXML ? tmp : 0; } this.notifyAboutNewItems(aTypeStr, newMailCounter, {from: newLastItem.getAttribute("from"), title: newLastItem.getAttribute("title")}); } this.newMailCounter = newMailCounter; this.mailPermCounter = this.mailCounter; break; } OBSERVER_SERVICE.notifyObservers(null, "Ya-Refresh-Data", aTypeStr); }, xmlHttpRequest: function(aUrl, aDetails) { var req = Cc["@mozilla.org/xmlextras/xmlhttprequest;1"].createInstance(Ci.nsIXMLHttpRequest); //req.mozBackgroundRequest = true; req.open(aDetails.data ? "POST" : "GET", aUrl, true); //req.channel.loadFlags |= Ci.nsIRequest.LOAD_BYPASS_CACHE; req.setRequestHeader("Cache-Control", "no-cache"); if (aDetails.data) { req.setRequestHeader("Content-Type", "application/x-www-form-urlencoded; charset=UTF-8"); req.setRequestHeader("Connection", "close"); } var target = req.QueryInterface(Ci.nsIDOMEventTarget); if (aDetails.callbackFunc) { target.addEventListener("load", aDetails.callbackFunc, false); target.addEventListener("error", aDetails.callbackFunc, false); } req.send(aDetails.data || null); return req; }, isReqError: function(aReq) { return !!(!aReq || aReq.type == "error" || !aReq.target || aReq.target.status != 200); }, get Counters() { return gYaUServices; }, get yaPartner() { return gYaPartner; }, get yaCity() { return gYaCity; }, get yaBookmarks() { return gYaBookmarks; }, get yaOverlay() { return gYaOverlay; }, get yaDefence() { return gYaDefence; }, get yaFTab() { return gYaFTab; }, get yaURLInfo() { return gYaURLInfo; }, getFeedsGroups: function(aCallback) { this.xmlHttpRequest("http://lenta.yandex.ru/count.xml", { callbackFunc: this.getFeedsGroupsCallback.bind(this, aCallback) }); }, getFeedsGroupsCallback: function(aReq, aCallback) { var mlist = false, doc = false; if (!this.isReqError(aReq)) doc = aReq.target.responseXML; if (doc) {//"no auth" case var _doc = this.domParser.parseFromString("<empty/>", "text/xml"); function createElement(aElementName) { return _doc.createElementNS(XULNS, aElementName); } var groups = doc.getElementsByTagName("group"); var mpopup = createElement("menupopup"); var last_group_id = this.feedsLastGroupId; var selected_item = 0; for (var i = 0; i < groups.length; i++) { var mi = createElement("menuitem"); mi.setAttribute("label", groups.item(i).getAttribute("title")); var group_id = groups.item(i).getAttribute("id"); if (group_id == last_group_id) selected_item = i; mi.setAttribute("group-id", group_id); mpopup.appendChild(mi); } mpopup.selectedIndex = selected_item; mlist = createElement("menulist"); mlist.appendChild(mpopup); mlist.setAttribute("id", "yasearch-feeds-select-group"); if (groups.length == 0) { mlist.setAttribute("disabled", "true"); mpopup.appendChild(createElement("menuitem")); } } if (aCallback) aCallback(mlist); }, get feedsCounter() { return this.isLogin ? (this.usersData[this.username]._feedsCounter || 0) : 0; }, set feedsCounter(val) { if (this.isLogin) this.usersData[this.username]._feedsCounter = Math.max(val, 0); }, get feedsLastGroupId() { return this.isLogin ? (this.usersData[this.username]._feedsLastGroupId || 0) : 0; }, set feedsLastGroupId(val) { if (this.isLogin) this.usersData[this.username]._feedsLastGroupId = val; }, feedsInsertNewItem: function(aData) { if (aData.group_id) { this.feedsLastGroupId = aData.group_id; this.xmlHttpRequest("http://lenta.yandex.ru/feed_add_url.xml", { callbackFunc: this.feedsInsertNewItemCallback.bind(this, aData), data: "url=" + encodeURIComponent(aData.url) + "&group_id=" + aData.group_id + "&ajax=1" }); } else if (aData.title && aData.title != "") { this.xmlHttpRequest("http://lenta.yandex.ru/feed_add_group_bar.xml", { callbackFunc: this.feedsInsertNewGroupCallback.bind(this, aData), data: "title=" + encodeURIComponent(aData.title) + "&ajax=1" }); } }, feedsInsertNewGroupCallback: function(aReq, aData) { let error; if (this.isReqError(aReq)) { error = "errorNewGroup1"; } else { let group_id; let pageXml = gYaSearchService.safeE4Xml(aReq.target.responseText, null, "page"); if (pageXml) group_id = pageXml.status.added.@id.toString(); if (group_id) aData.group_id = group_id; else error = "errorNewGroup2"; } return error ? aData.callback(error) : this.feedsInsertNewItem(aData); }, feedsInsertNewItemCallback: function(aReq, aData) { this.feedsLastGroupId = aData.group_id; var error; if (this.isReqError(aReq)) error = "errorNewItem1"; else if (aReq.target.responseText.indexOf("ok") != 0) error = "errorNewItem2"; return aData.callback(error); }, get moneyCounter() { return this.isLogin ? (this.usersData[this.username]._moneyCounter || 0) : 0; }, set moneyCounter(val) { if (this.isLogin) this.usersData[this.username]._moneyCounter = Math.max(val, 0); }, get guidMessageTS() { return this.isLogin && this.usersData[this.username]._guidLastMsgTs ? this.usersData[this.username]._guidLastMsgTs : (this.getCharPref("yasearch.guid.lastMsg") || ""); }, set guidMessageTS(val) { val = val.toString(); if (this.isLogin) this.usersData[this.username]._guidLastMsgTs = val; this.setCharPref("yasearch.guid.lastMsg", val); }, get guidUpdateDS() { return this.getIntPref("yasearch.guid.lastUpdate"); }, set guidUpdateDS(val) { val = val ? Math.abs(G_TIME_NOW/DAY_SECS) : 0; this.setIntPref("yasearch.guid.lastUpdate", val); }, get mailCounter() { return this.isLogin ? (this.usersData[this.username]._mailCounter || 0) : 0; }, set mailCounter(val) { if (this.isLogin) this.usersData[this.username]._mailCounter = Math.max(val, 0); }, get newMailCounter() { return this.isLogin ? (this.usersData[this.username]._newMailCounter || 0) : 0; }, set newMailCounter(val) { if (this.isLogin) this.usersData[this.username]._newMailCounter = Math.max(val, 0); }, get mailPermCounter() { return this.isLogin ? (this.usersData[this.username]._mailPermCounter || 0) : 0; }, set mailPermCounter(val) { if (this.isLogin) this.usersData[this.username]._mailPermCounter = Math.max(val, 0); }, get mailDOMMenuDoc() { if (!this.isLogin || !this.usersData[this.username]._mailDOMMenuDoc) return false; return this.usersData[this.username]._mailDOMMenuDoc; }, set mailDOMMenuDoc(doc) { if (this.isLogin) this.usersData[this.username]._mailDOMMenuDoc = doc; }, get mailData() { return {"count": this.mailCounter, "permCount": this.mailPermCounter, "nodes": this.mailDOMMenuDoc ? this.getDOMDocContent("mail-items", this.mailDOMMenuDoc) : false, "lastmaxid": this.mailLastMaxId, "newCount": this.newMailCounter}; }, get mailLastMaxId() { if (!this.isLogin || !this.usersData[this.username]._mailLastMaxId) return "0"; return this.usersData[this.username]._mailLastMaxId; }, set mailLastMaxId(id) { if (this.isLogin) this.usersData[this.username]._mailLastMaxId = id.toString(); }, get mailLastCheckIsOutOfDate() { if (!this.isLogin) return false; let lastCheckTime = this.usersData[this.username]._mailLastCheckTime || 0; return Math.abs(lastCheckTime - G_TIME_NOW) > (30 * MIN_SEC); }, set mailLastCheckIsOutOfDate(val) { if (this.isLogin) this.usersData[this.username]._mailLastCheckTime = val ? 0 : G_TIME_NOW; }, bookmarksPrepeareDialog: function(aCallback) { this.xmlHttpRequest("http://zakladki.yandex.ru/bar/struct.xml?newdescr=true&" + getNCRndStr(), { callbackFunc: this.bookmarksPrepeareDialogCallback.bind(this, aCallback) }); }, bookmarksPrepeareDialogCallback: function(aReq, aCallback) { var res; if (this.isReqError(aReq)) { res = "lost_connection"; } else if (!this.isLogin) { res = "auth_required"; } else { var bookmarksResponse = this.yaBookmarks.getServerResponse(aReq.target.responseText); if (bookmarksResponse.error && bookmarksResponse.error !== "reg_required") { res = bookmarksResponse.error; } else { var data = bookmarksResponse.error ? "<err/>" : bookmarksResponse.xml.toString(); if (res = this.getDOMDocContent("bar-bookmarks-folders", this.domParser.parseFromString(data, "text/xml"))) res.setAttribute("disabled", "true"); else res = "service"; } } if (aCallback) aCallback(res); }, bookmarksGetItemById: function(aId) { let item = this.bookmarksRawXml.bookmarks..*.(function::attribute("id") == aId)[0]; return { id: item.@id.toString(), type: item.localName().toString(), url: item.@url.toString(), name: item.@name.toString(), descr: item.descr.toString(), tags: item.@tags.toString(), parentId: item.@folder_id.toString() || item.@parent_id.toString() }; }, bookmarksEditItem: function(aItem) { if (!aItem.id) throw "bookmarksEditItem: no ID"; if (aItem.nfolder != "") { var url = "http://zakladki.yandex.ru/bar/addfolder.xml?" + getNCRndStr(); url = this.appendStatData2Url(url,{}); var data = "name=" + encodeURIComponent(aItem.nfolder) + "&parent_id=" + aItem.folder; this.xmlHttpRequest(url, {data: data, callbackFunc: this.bookmarksInsertNewFolderInXML.bind(this, aItem)}); } else { var old = aItem._old_info; aItem.tags = this.yaBookmarks.formatTagsString(aItem.tags); if (old.name != aItem.name || old.descr != aItem.descr || old.url != aItem.url || old.tags != aItem.tags) { var type = aItem.type; var url = "http://zakladki.yandex.ru/bar/update" + type + ".xml?" + getNCRndStr(); url = this.appendStatData2Url(url,{}); var data = type + "_id=" + aItem.id + "&name=" + encodeURIComponent(aItem.name) + "&descr=" + encodeURIComponent(aItem.descr) + "&tags=" + encodeURIComponent(aItem.tags); if (type == "link") data += "&url=" + encodeURIComponent(aItem.url); this.xmlHttpRequest(url, { data: data, callbackFunc: this.bookmarksEditItemInXML.bind(this, aItem) }); } else if (aItem.folderOld != aItem.folder) { this.bookmarksMoveItem(aItem); } else { return aItem.callback(); } } }, bookmarksEditItemInXML: function(aReq, aItem) { var res; if (this.isReqError(aReq)) { res = "lost_connection"; } else if (!this.isLogin) { res = "auth_required"; } else { var bookmarksResponse = this.yaBookmarks.getServerResponse(aReq.target.responseText); if (bookmarksResponse.error) { res = bookmarksResponse.error; } else { if (!bookmarksResponse.xml.ok.length()) { res = "service"; } else { var bookmarks = this.usersData[this.username]._bookmarksRawXml.bookmarks; var elem = (aItem.type == "folder" ? bookmarks..folder : bookmarks..link).(@id == aItem.id)[0]; elem.@name = aItem.name; elem.@url = aItem.url; elem.descr = aItem.descr; elem.@tags = this.yaBookmarks.formatTagsString(aItem.tags); this.yaBookmarks.refreshBookmarksDOMMenu(); if (aItem.folderOld != aItem.folder) { this.bookmarksMoveItem(aItem); return; } } } } return aItem.callback(res); }, bookmarksMoveItem: function(aItem) { if (!aItem.id) throw "bookmarksMoveItem: no ID"; var url = "http://zakladki.yandex.ru/bar/move.xml?" + getNCRndStr(); url = this.appendStatData2Url(url,{}); var data = "folder_id=" + aItem.folder + "&" + (aItem.type == "folder" ? "fid" : "link_id") + "=" + aItem.id; this.xmlHttpRequest(url, { data: data, callbackFunc: this.bookmarksMoveItemInXML.bind(this, aItem) }); }, bookmarksMoveItemInXML: function(aReq, aItem) { var res; if (this.isReqError(aReq)) { res = "lost_connection"; } else if (!this.isLogin) { res = "auth_required"; } else { var bookmarksResponse = this.yaBookmarks.getServerResponse(aReq.target.responseText); if (bookmarksResponse.error) { res = bookmarksResponse.error; } else { if (!bookmarksResponse.xml.ok.length()) { res = "service"; } else { var bookmarks = this.usersData[this.username]._bookmarksRawXml.bookmarks; var elem = (aItem.type == "folder" ? bookmarks..folder : bookmarks..link).(@id == aItem.id); if (elem[0]) { var clone = new XML(elem[0]); var inFolder = bookmarks..folder.(@id == aItem.folder), inFolderId = inFolder.@id.toString(); if (inFolder.@id.toString() == "") { inFolder = bookmarks; inFolderId = "0"; } var type = aItem.type; switch (type) { case "folder": clone.@parent_id = inFolderId; var len = inFolder.folder.(@name < aItem.name).length()-1; if (len == -1) inFolder.folder = clone + inFolder.folder; else inFolder.folder[len] += clone; break; case "link": clone.@folder_id = inFolderId; var len = inFolder.links.link.(@name < aItem.name).length()-1; if (len == -1) inFolder.links.link = clone + inFolder.links.link; else inFolder.links.link[len] += clone; break; } delete elem[0]; } } } } this.yaBookmarks.refreshBookmarksDOMMenu(); return aItem.callback(res); }, bookmarksDeleteItem: function(aItem) { if (!aItem.id) throw "bookmarksDeleteItem: no ID"; var url = "http://zakladki.yandex.ru/bar/del.xml?" + getNCRndStr(); url = this.appendStatData2Url(url, {}); var data = (aItem.type == "folder" ? "fid" : "link_id") + "=" + encodeURIComponent(aItem.id); this.xmlHttpRequest(url, {data: data, callbackFunc: this.bookmarksDeleteItemInXML.bind(this, aItem)}); }, bookmarksDeleteItemInXML: function(aReq, aItem) { var res; if (this.isReqError(aReq)) { res = "lost_connection"; } else if (!this.isLogin) { res = "auth_required"; } else { var bookmarksResponse = this.yaBookmarks.getServerResponse(aReq.target.responseText); if (bookmarksResponse.error) { res = bookmarksResponse.error; } else { if (!bookmarksResponse.xml.ok.length()) { res = "service"; } else { var bookmarks = this.usersData[this.username]._bookmarksRawXml.bookmarks; var elem = (aItem.type == "folder" ? bookmarks..folder : bookmarks..link).(@id == aItem.id); if (elem[0]) { delete elem[0]; this.yaBookmarks.refreshBookmarksDOMMenu(); } } } } return aItem.callback(res); }, bookmarksSubscribeCallback: function(aReq, aItem) { this.bookmarksInsertNewItem(aItem); }, bookmarksInsertNewItem: function(aItem) { if (this.yaBookmarks.isRegRequired) { this.yaBookmarks.isRegRequired = null; if (!this.yaBookmarks.isRegRequired) { this.xmlHttpRequest("http://passport.yandex.ru/passport?mode=subscribe&from=zakladki", { callbackFunc: this.bookmarksSubscribeCallback.bind(this, aItem) }); return; } } if (aItem.nfolder) { var url = "http://zakladki.yandex.ru/bar/addfolder.xml?" + getNCRndStr(); url = this.appendStatData2Url(url, {}); var data = "name=" + encodeURIComponent(aItem.nfolder) + "&parent_id=" + aItem.folder; this.xmlHttpRequest(url, {data: data, callbackFunc: this.bookmarksInsertNewFolderInXML.bind(this, aItem)}); } else { var url = "http://zakladki.yandex.ru/bar/addlink.xml?" + getNCRndStr(); url = this.appendStatData2Url(url, {}); var yaruDataAppend = (aItem.yaru && ("feed_id" in aItem.yaru) && ("status" in aItem.yaru)) ? ("&feed_id=" + encodeURIComponent(aItem.yaru.feed_id) + "&status=" + encodeURIComponent(aItem.yaru.status)) : ""; var data = "name=" + encodeURIComponent(aItem.name) + "&url=" + encodeURIComponent(aItem.url) + "&descr=" + encodeURIComponent(aItem.descr) + "&tags=" + encodeURIComponent(aItem.tags) + "&folder_id=" + (aItem.folder || 0) + "&newfolder=" + yaruDataAppend + "&from=barff"; this.xmlHttpRequest(url, {data: data, callbackFunc: this.bookmarksInsertNewLinkInXML.bind(this, aItem)}); } }, bookmarksInsertNewFolderInXML: function(aReq, aItem) { var res; if (this.isReqError(aReq)) { res = "lost_connection"; } else if (!this.isLogin) { res = "auth_required"; } else { var bookmarksResponse = this.yaBookmarks.getServerResponse(aReq.target.responseText); if (bookmarksResponse.error) { res = bookmarksResponse.error; } else { var newFolderId = bookmarksResponse.xml.ok[0].@id.toString(); if (!newFolderId) { res = "service"; } else { var bookmarks = this.usersData[this.username]._bookmarksRawXml.bookmarks; var elem = bookmarks..folder.(@id == aItem.folder); var parent = elem.@id.toString() == "" ? bookmarks : elem; var parentId = parent.@id.toString() == "" ? "0" : parent.@id.toString(); if (bookmarks..folder.(@id == newFolderId).length() == 0) { var newItem = new XML('<folder id="' + newFolderId + '" parent_id="' + parentId + '"><links/></folder>'); newItem.@name = aItem.nfolder; var len = parent.folder.(@name < aItem.nfolder).length()-1; if (len == -1) parent.folder = newItem + parent.folder; else parent.folder[len] += newItem; this.yaBookmarks.refreshBookmarksDOMMenu(); } aItem.nfolder = ""; aItem.folder = newFolderId; this.yaBookmarks.lastUsedFolder = newFolderId; if (aItem.folderOld) { this.bookmarksEditItem(aItem); } else { this.bookmarksInsertNewItem(aItem); } } } } if (res) return aItem.callback(res); }, bookmarksInsertNewLinkInXML: function(aReq, aItem) { var res; if (this.isReqError(aReq)) { res = "lost_connection"; } else if (!this.isLogin) { res = "auth_required"; } else { var bookmarksResponse = this.yaBookmarks.getServerResponse(aReq.target.responseText); if (bookmarksResponse.error) { res = bookmarksResponse.error; } else { var newLinkId = bookmarksResponse.xml.ok[0].@id.toString(); if (!newLinkId || newLinkId == "0") { res = "service"; } else { if (bookmarksResponse.xml.ok[0].@yaru_link.toString()) { res = this.getDOMDocContent2("bookmarks/xsl-yaru-post-props.xsl", this.domParser.parseFromString(bookmarksResponse.xml.toSource(), "text/xml")); } else { res = null; } try { var _uri = Cc["@mozilla.org/network/io-service;1"].getService(Ci.nsIIOService).newURI(aItem.url, null, null); aItem.url = "hostPort" in _uri ? [_uri.scheme, "://", (_uri.scheme == "file" ? "/" : ""), _uri.hostPort, _uri.path].join("") : _uri.spec; } catch(e) { aItem.url = "http://" + aItem.url; } var bookmarks = this.usersData[this.username]._bookmarksRawXml.bookmarks; var elem = bookmarks..folder.(@id == aItem.folder); var parent = (elem.@id.toString() == "" ? bookmarks : elem).links; var duplicate = !!(bookmarksResponse.xml.ok[0].@duplicate.toString() > ""); duplicate = duplicate && parent.link.(@id == newLinkId).length(); if (!duplicate) { var newItem = new XML('<link id="' + newLinkId + '" folder_id="' + aItem.folder + '"/>'); newItem.@name = aItem.name; newItem.@url = aItem.url; newItem.descr = aItem.descr; newItem.@tags = aItem.tags; var len = parent.link.(@name < aItem.name).length()-1; if (len == -1) parent.link = newItem + parent.link; else parent.link[len] += newItem; } this.yaBookmarks.refreshBookmarksDOMMenu(); } } } return aItem.callback(res); }, get bookmarksDOMMenu() { if (!this.isLogin) return this.bookmarksDOMMenuDefault; if (!this.usersData[this.username].bookmarksDOMMenu) this.bookmarksDOMMenu = false; return this.usersData[this.username].bookmarksDOMMenu.cloneNode(true); }, get bookmarksDOMMenuDefault() { if (!this._bookmarksDOMMenuDefault) this._bookmarksDOMMenuDefault = this.getDOMDocContent("bar-bookmarks", this.domParser.parseFromString("<page><bookmarks/></page>", "text/xml")); return this._bookmarksDOMMenuDefault.cloneNode(true); }, set bookmarksDOMMenu(aBookmarksXML) { if (!this.isLogin) return false; this.usersData[this.username]._bookmarksRawXml = aBookmarksXML || this.bookmarksRawXml; if (aBookmarksXML) this.usersData[this.username]._bookmarksRawXml.@ts = G_TIME_NOW; this.usersData[this.username].bookmarksDOMMenu = this.getDOMDocContent2("xsl-templ/xsl-bar-bookmarks.xsl", this.domParser.parseFromString(this.usersData[this.username]._bookmarksRawXml, "text/xml"), { addToFolderOnTop: this.getBoolPref("yasearch.general.ui.bookmarks.showaddtofolderontop") }); this.yaBookmarks.bookmarksCache.clear(true);//[2do] }, get bookmarksRawXml() { return (this.isLogin && this.usersData[this.username]._bookmarksRawXml) ? this.usersData[this.username]._bookmarksRawXml : new XML("<page><bookmarks/></page>"); }, bookmarksGetLinksInFolder: function(aFolderId) { let urlArray = []; let folder = aFolderId ? this.bookmarksRawXml.bookmarks..folder.(@id == aFolderId) : this.bookmarksRawXml.bookmarks; for each (var link in folder.links.link) urlArray.push(link.@url.toString()); return urlArray; }, get bookmarksIsOutOfDate() { if (this.isLogin && !this.usersData[this.username]._bookmarksRawXml) return true; let lastCheckTime = this.parseIntFromStr(this.bookmarksRawXml.@ts); return !!(lastCheckTime && (Math.abs(G_TIME_NOW - lastCheckTime) > DAY_SECS)) }, setNotifyTimer: function(cancel) { if (!this._notifyTimer) { this._notifyTimer = Cc["@mozilla.org/timer;1"].createInstance(Ci.nsITimer); this._notifyTimer.initWithCallback(this, 1000, Ci.nsITimer.TYPE_REPEATING_SLACK); } else if (cancel) { this._runnedNotifications = []; this._notifyTimer.cancel(); this._notifyTimer = null; } }, notify: function(aTimer) { if (!this._runnedNotifications || this._runnedNotifications.length < 1) return this.setNotifyTimer("cancel"); var notif = this._runnedNotifications[0]; if (notif.isShowing == true) return; if (this.getBoolPref("yasearch." + notif.type + ".ui.notification.enabled")) { notif.isShowing = true; var msg = [(notif.type == "mail" && notif.nmb == 0) ? this.getFormattedString("mailNotificationMsgPlus", [this.maxUnreadInXML]) : this.getFormattedStringL18End(notif.type + "NotificationMsg", [notif.nmb])]; if (notif.type == "mail") { if (notif.nmb != 1) msg[0] += this.getString("mailNotificationMsgLast"); msg.push([notif.mdata.from, notif.mdata.title]); } this.showAlert(this.getString(notif.type + "NotificationTitle"), msg, notif.type); } else { this._runnedNotifications.shift(); } if (this.getBoolPref("yasearch." + notif.type + ".ui.soundnotification.enabled")) this.playSoundURL(this.getComplexValue("yasearch." + notif.type + ".ui.soundnotification.uri")); }, playSoundURL: function(aSoundUrl) { if (!aSoundUrl || !aSoundUrl.length) return; var uri; try { if (aSoundUrl.indexOf("file://") == -1) { var tempLocalFile = Cc["@mozilla.org/file/local;1"].createInstance(Ci.nsILocalFile); tempLocalFile.initWithPath(aSoundUrl); uri = this.makeFileURI(tempLocalFile); } else { uri = this.makeURI(aSoundUrl); } this.soundService.play(uri); } catch(e) {} }, notifyAboutNewItems: function(aType, aNewNum, aMailData) { switch (aType) { case "lenta": aType = "feeds"; break; case "mailList": //~ case "mail": aType = "mail"; break; default: return; } if (this.getBoolPref("yasearch." + aType + ".ui.notification.enabled") || this.getBoolPref("yasearch." + aType + ".ui.soundnotification.enabled")) { this._runnedNotifications.push({type: aType, nmb: aNewNum, mdata: aMailData, isShowing: false}); this.setNotifyTimer(); } }, _showAlertWithGrowl: function(title, msg, type) { if (this.AppInfo.OS.isMacOS) { try { var listener = { observe: function(aSubject, aTopic, aData) { if (aTopic == "alertclickcallback" && (aData == "mail" || aData == "feeds")) gYaSearchService.loadConditionalURI(aData, "tab", {action: (aData == "mail" ? 1040 : 1120)}); } } var alertsService = Cc["@mozilla.org/alerts-service;1"].getService(Ci.nsIAlertsService); alertsService.showAlertNotification(CHROME_IMAGES + "bar-logo.png", title.split(":")[0], msg, false, type, listener); return true; } catch(e) {} } return false; }, showAlert: function(title, msg, type) { if (this._showAlertWithGrowl(title, msg, type)) { this._runnedNotifications.shift(); return; } let flags = "chrome,popup=yes"; if (!this.AppInfo.browser.isGreaterThenFx35) flags += ",titlebar=no"; let url = type ? CHROME_CONTENT + "alerts/timed.alert.xul" : "chrome://global/content/alerts/alert.xul"; var alertWin = this.windowWatcher.openWindow(null, url, "_blank", flags, null); alertWin.arguments = [CHROME_IMAGES + "bar-logo.png", title, msg, (type ? type : false), this.timedAlertListener]; }, showPermanentAlert: function(title, msg, image, cookie) { let flags = "chrome,popup=yes"; if (!this.AppInfo.browser.isGreaterThenFx35) flags += ",titlebar=no"; var alertWin = this.windowWatcher.openWindow(null, CHROME_CONTENT + "alerts/permanent.alert.xul", "_blank", flags, null); alertWin.arguments = [image && image != "" ? image : CHROME_IMAGES + "bar-logo.png", title, msg, (cookie||""), this.permanentAlertListener]; }, timedAlertListener: { observe: function(aSubject, aTopic, aData) { if (aTopic == "alertfinished" && gYaSearchService._runnedNotifications) gYaSearchService._runnedNotifications.shift(); } }, permanentAlertListener: { observe: function(aSubject, aTopic, aData) { if (aTopic == "alertfinished") { switch (aData) { case "": case "error": case "installed": break; case "cancelled": gYaSearchService.guidUpdateDS = true; break; default: gYaSearchService.guidMessageTS = aData; } } } }, decMailCounter: function(aMailId) { if (this.mailDOMMenuDoc && this.mailDOMMenuDoc.hasChildNodes()) { var elem = this.xPathEvaluator.evaluate("//item/item[@url='" + aMailId + "']", this.mailDOMMenuDoc, null, this.unSnapshotType, null).snapshotItem(0); if (elem) { var parent = elem.parentNode; if (parent.getElementsByTagName("item").length == 1) { parent.parentNode.removeChild(parent); } else { parent.removeChild(elem); } this.mailCounter--; this.mailPermCounter--; new G_Timer(function(){OBSERVER_SERVICE.notifyObservers(null, "Ya-Refresh-Data", "mailList")}, 1); this.mailLastCheckIsOutOfDate = true; this.refreshHTTPData("mail", null, 10000); } } }, KeyCorrector: { STATE_DISABLED: 0, STATE_RUNNED: 1, STATE_STOPPED: 2, _statePrefName: "yasearch.general.ui.urlbar.corrector.state", _checkStateValue: function(aValue) { if (aValue > this.STATE_STOPPED || aValue < this.STATE_DISABLED) aValue = this.STATE_STOPPED; return aValue; }, get currentState() { return this._checkStateValue(gYaSearchService.getIntPref(this._statePrefName)); }, set currentState(val) { gYaSearchService.setIntPref(this._checkStateValue(this._statePrefName), val); return val; }, get keyConvTable() { return gYaSearchService.windowsOS ? { withoutShift: { 192: 96, 49: 49, 50: 50, 51: 51, 52: 52, 53: 53, 54: 54, 55: 55, 56: 56, 57: 57, 48: 48, 109: 45, 61: 61, 81: 113, 87: 119, 69: 101, 82: 114, 84: 116, 89: 121, 85: 117, 73: 105, 79: 111, 80: 112, 219: 91, 221: 93, 220: 92, 65: 97, 83: 115, 68: 100, 70: 102, 71: 103, 72: 104, 74: 106, 75: 107, 76: 108, 59: 59, 222: 39, 90: 122, 88: 120, 67: 99, 86: 118, 66: 98, 78: 110, 77: 109, 188: 44, 190: 46, 191: 47 }, withShift: { 192: 126, 49: 33, 50: 64, 51: 35, 52: 36, 53: 37, 54: 94, 55: 38, 56: 42, 57: 40, 48: 41, 109: 95, 61: 43, 81: 81, 87: 87, 69: 69, 82: 82, 84: 84, 89: 89, 85: 85, 73: 73, 79: 79, 80: 80, 219: 123, 221: 125, 220: 124, 65: 65, 83: 83, 68: 68, 70: 70, 71: 71, 72: 72, 74: 74, 75: 75, 76: 76, 59: 58, 222: 34, 90: 90, 88: 88, 67: 67, 86: 86, 66: 66, 78: 78, 77: 77, 188: 60, 190: 62, 191: 63 } } : null }, __charConvTable: null, get charConvTable() { if (!this.__charConvTable) { var withoutShift = {}, withShift = {}; var cirChars = UConverter.ConvertToUnicode( "╨╣╤å╤â╨║╨╡╨╜╨│╤ê╤ë╨╖╤à╤è╤ä╤ï╨▓╨░╨┐╤Ç╨╛╨╗╨┤╨╢╤ì╤Å╤ç╤ü╨╝╨╕╤é╤î╨▒╤Ä╤æ╨Ö╨ª╨ú╨Ü╨ò╨¥╨ô╨¿╨⌐╨ù╨Ñ╨¬╨ñ╨½╨Æ╨É╨ƒ╨á╨₧╨¢╨ö╨û╨¡╨»╨º╨í╨£╨ÿ╨ó╨¼╨æ╨«╨ü╤û╨å"); var latChars = "qwertyuiop[]asdfghjkl;'zxcvbnm,.`QWERTYUIOP[]ASDFGHJKL;'ZXCVBNM,.`sS"; var cirCharsShift = UConverter.ConvertToUnicode('╤à╤è╨╢╤ì╨▒╤Ä╤æ"*,.;Γäû'); var latCharsShift = '{}:"<>~@$^&*#'; var i=0, ch; while ((ch = cirChars[i])) withoutShift[ch] = latChars[i++]; i=0; while ((ch = cirCharsShift[i])) withShift[ch] = latCharsShift[i++]; this.__charConvTable = { withoutShift: withoutShift, withShift: withShift }; } return this.__charConvTable; } }, // ********************************************** Bloggers: { cachedTabs: {}, _tabTimer: null, _setTimer: function(aTabData, aVal) { if (this._tabTimer) this._tabTimer.cancel(); else if (aVal) this._tabTimer = Cc["@mozilla.org/timer;1"].createInstance(Ci.nsITimer); if (!aVal) return; this._tabTimer.initWithCallback({ tab: aVal.tab, url: aVal.url, notify: function(aTimer) { let bloggers = gYaURLInfo.getBloggers(this.url); if (!bloggers) return; var _self = gYaSearchService.Bloggers; if (bloggers.windowState & gYaURLInfo.BLOGGERS_STATE_TIMED_REQUEST) { bloggers.windowState = gYaURLInfo.BLOGGERS_STATE_REQUEST; _self.setBloggersData(false, this.tab, this.url); let _url = "http://blogs.yandex.ru/bar.xml?text=" + encodeURIComponent('!link="' + this.url + '"') + "&count=" + bloggers.value + (this.manual ? "&" + getNCRndStr() : ""); gYaSearchService.xmlHttpRequest( _url, {callbackFunc: _self.setBloggersData.bind(_self, this.tab, this.url)} ); } } }, aTabData._timeout, Ci.nsITimer.TYPE_ONE_SHOT); }, clearTabData: function(aTabId) { delete this.cachedTabs[aTabId]; }, getBloggersData: function(aTab, aSkipCache, aTimeout, aManual) { if (!(aTab && aTab.selected)) return; let bloggers = gYaURLInfo.getBloggers(aTab.linkedBrowser.currentURI); if (!bloggers) return; let url = bloggers.url, aTabId = aTab.linkedPanel, tData = this.cachedTabs[aTabId]; if (!tData) tData = this.cachedTabs[aTabId] = { visible: false }; tData.url = url; tData._timeout = aTimeout ? 5 : 5000; this._setTimer(); if ((bloggers.buttonState === gYaURLInfo.BLOGGERS_STATE_UNKNOWN) || (aSkipCache && !(bloggers.buttonState & gYaURLInfo.BLOGGERS_STATE_REQUEST))) { bloggers.buttonState = gYaURLInfo.BLOGGERS_STATE_UNKNOWN; if (aManual) { bloggers.manual = true; gYaSearchService.notifyBusyStateOfRequest(null, true, true, "yasearch-bloggers"); } gYaSearchService.getCY(url, aTab.linkedBrowser.webProgress, false); } else if (bloggers.value > 0 && tData && this.isWindowVisible(aTab) && ((bloggers.windowState & gYaURLInfo.BLOGGERS_STATE_UNKNOWN) || (bloggers.windowState & gYaURLInfo.BLOGGERS_STATE_TIMED_REQUEST) || (aSkipCache && !(bloggers.windowState & gYaURLInfo.BLOGGERS_STATE_REQUEST)))) { bloggers.windowState = gYaURLInfo.BLOGGERS_STATE_TIMED_REQUEST; this._setTimer(tData, {tab: aTab, url: url}); } this.setBloggersData(false, aTab, url); }, persistScrollPosition: function(aURL, aYPos) { let bloggers = gYaURLInfo.getBloggers(aURL); if (bloggers) bloggers.scroll = aYPos; }, switchWindowMode: function(aMode) { this._fullMode = aMode === null ? !this._fullMode : aMode; return this._fullMode; }, hideTopModeWindow: function() { if (this._fullMode) for each (let tabData in this.cachedTabs) if (tabData.visible) tabData.visible = false; }, persistWindowVisible: function(aTab, aVisible) { let tData = this.cachedTabs[aTab.linkedPanel]; if (!tData) tData = this.cachedTabs[aTab.linkedPanel] = {}; tData.visible = aVisible; }, isWindowVisible: function(aTab) { if (this._fullMode) return true; if (!aTab.selected) return false; let tData = this.cachedTabs[aTab.linkedPanel]; return !!(tData && tData.visible); }, setBloggersData: function(aReq, aTab, aUrl) { let bloggers = gYaURLInfo.getBloggers(aUrl); if (!bloggers) return; if (bloggers.manual) { bloggers.manual = false; gYaSearchService.notifyBusyStateOfRequest(null, false, true, "yasearch-bloggers"); } if (aReq != false) { bloggers.windowState = gYaURLInfo.BLOGGERS_STATE_ERROR; if (!gYaSearchService.isReqError(aReq)) { let serverDate; try { serverDate = new Date(aReq.target.getResponseHeader("Date")); if (serverDate != "Invalid Date") serverDate = new Date(serverDate.getTime() + serverDate.getTimezoneOffset() * 60 * 1000 + 3 * 60 * 60 * 1000); if (serverDate == "Invalid Date") serverDate = null; } catch(e) {} let doc = gYaSearchService.getDOMDocContent2("xsl-templ/xsl-bloggers-data.xsl", gYaSearchService.domParser.parseFromString(aReq.target.responseText, "text/xml")); if (doc && doc.localName == "vbox") { bloggers.windowState = gYaURLInfo.BLOGGERS_STATE_RESPONSE; doc.firstChild.setAttribute("location", bloggers.url); if (serverDate) { Array.forEach(doc.getElementsByTagName("label"), function(aLabel) { if (aLabel.getAttribute("class") == "ya-blogger-time") { var postDate = this.getDateDiffString(serverDate, this.getDateFromString(aLabel.getAttribute("value"))); if (postDate) aLabel.setAttribute("value", postDate); } }, this); } Array.forEach(doc.getElementsByTagName("description"), function(aDescription) { var node = aDescription.firstChild; if (node && node.nodeName == "#text") node.nodeValue = node.nodeValue.replace(/([\/\-&\?\.])/g, "$1\u200B") .replace(/(\S{15})(\S{15})/g, "$1\u200B$2"); }) bloggers.content = doc; } } else { gYaSearchService.log("setBloggersData got bad request result"); } } try { if (aTab.selected) aTab.ownerDocument.defaultView.Ya.Bloggers.setData(bloggers); } catch(e) {} }, getDateFromString: function(aString) { let res = aString.match(/(\d{1,2})\.(\d{1,2})\.(\d{4})(?:\s+(\d{1,2})\:(\d{1,2}))?/) ? new Date(RegExp.$3, (RegExp.$2 * 1) - 1, RegExp.$1, RegExp.$4, RegExp.$5) : null; return (!res && res == "Invalid Date") ? null : res; }, _getFormatedTime: function(aDate) { return [aDate.getHours(), ("0" + aDate.getMinutes()).slice(-2)].join(":"); }, getDateDiffString: function(aCurrentDate, aDate) { if (!(aCurrentDate instanceof Date) || !(aDate instanceof Date)) return null; let diff = aCurrentDate.getTime() - aDate.getTime(); if (diff < 0) return null; let res = [], strType = "year"; if (diff < DAY_SECS) strType = "today"; if (aCurrentDate.getDate() != aDate.getDate()) strType = "yesterday"; if (diff >= DAY_SECS * 2) strType = "month"; if (aCurrentDate.getYear() != aDate.getYear()) strType = "year"; switch (strType) { case "year": res = [aDate.getDate(), this.dateStrings.months[aDate.getMonth()], aDate.getFullYear()]; break; case "month": res = [aDate.getDate(), this.dateStrings.months[aDate.getMonth()]]; res.push(this._getFormatedTime(aDate)); break; case "today": case "yesterday": res = [this.dateStrings[strType]]; res.push(this._getFormatedTime(aDate)); break; } return res.join(" "); }, _dateStrings: null, get dateStrings() { if (!this._dateStrings) { this._dateStrings = { months: gYaSearchService.getString("dateMonths").toLowerCase().split(","), today: gYaSearchService.getString("dateToday"), yesterday: gYaSearchService.getString("dateYesterday") } } return this._dateStrings; } }, // ********************************************** _browserButtons: null, get browserButtons() { if (!this._browserButtons) this._browserButtons = this.buttonsInfo || {}; return this._browserButtons; }, set browserButtons(val) { this._browserButtons = val; }, webProgressListener: { _servicesRe: /^https?:\/\/(?:((?:web)?mail|lenta(?:\-ng)?|money|fotki)\.yandex|[^\/]*\.(ya)|(moikrug))\.(?:ru|ua)\/(.*)/i, _checkNeedRefreshData: function(aURL, aButtons) { aURL = "" + aURL; if (!gYaSearchService.isLogin || !aURL.match(this._servicesRe)) return; var service = (RegExp.$1 || RegExp.$2 || RegExp.$3).toLowerCase(); var path = RegExp.$4.toLowerCase(); var timeoutDelay = 5000; switch (service) { case "mail": timeoutDelay = 70000; if (aButtons.mail && /^(modern|classic|neo)\/messages(\?|$)/.test(path) && gYaSearchService.Counters.getCount("mail") > 0) gYaSearchService.refreshHTTPData("mail", null, timeoutDelay); break; case "lenta-ng": case "lenta": if (aButtons.lenta && /^(un)?read.xml/.test(path) && gYaSearchService.Counters.getCount("lenta") > 0) gYaSearchService.refreshHTTPData("lenta", null, timeoutDelay); break; case "fotki": if (aButtons.fotki) { var needRefresh = false; if (/\/favorites$/.test(path)) { if (gYaSearchService.Counters.getCount("fotki") > 0) needRefresh = true; } else if (/\/comments$/.test(path)) { if (gYaSearchService.Counters.getCount("fotki", "comments") > 0) needRefresh = true; } if (needRefresh) gYaSearchService.refreshHTTPData("fotki", null, timeoutDelay); } break; case "money": if (path == "" || path == "prepaid.xml" || path == "shops.xml") gYaSearchService.refreshHTTPData("money", null, timeoutDelay); break; case "ya": if (path && path.indexOf("replies_history_unread.xml") == 0) gYaSearchService.refreshHTTPData("yaru", null, timeoutDelay); break; case "moikrug": if (path && (/^threads\/?$/.test(path) || /^threads\/\?ncrnd/.test(path)) && gYaSearchService.Counters.getCount("moikrug") > 0) { gYaSearchService.refreshHTTPData("moikrug", null, timeoutDelay); } break; default: break; } }, _getUrlFromLocation: function(aLocation) { let url = gYaURLInfo.getURL(aLocation); return url ? url.toString() : false; }, _checkIsTopWindowRequested: function(aWebProgress, aRequest) { let reqWindow = false, topWindow = false; try { reqWindow = aWebProgress.DOMWindow; topWindow = reqWindow.top; } catch(e) {} return (topWindow && topWindow === reqWindow && (arguments.length == 1 || topWindow.location.toString() === aRequest.name.toString()) ); }, _getDataSumm: function(aWebProgress) { let dataSumm = {}; if (aWebProgress && !aWebProgress.isLoadingDocument) { let httpStatus = false; try { if ("currentDocumentChannel" in aWebProgress) { httpStatus = aWebProgress.currentDocumentChannel .QueryInterface(Ci.nsIHttpChannel) .responseStatus; } } catch(e) {} dataSumm = (aWebProgress.chromeEventHandler.yaSearchTHandler || {}).dataSumm || {}; dataSumm.httpStatus = httpStatus; } return dataSumm; }, onPageShowInBackground: function(aWebProgress, aButtons) { let url = this._getUrlFromLocation(aWebProgress.currentURI); if (url) this._checkNeedRefreshData(url, aButtons); }, onLocationChange: function(aWebProgress, aButtons) { gYaSearchService.browserButtons = aButtons; if (!aButtons.navigElements) return; if (!this._checkIsTopWindowRequested(aWebProgress)) return; let url = this._getUrlFromLocation(aWebProgress.currentURI); gYaSearchService.getCY(url, aWebProgress, true, null, this._getDataSumm(aWebProgress)); }, onPageStateStart: function(aWebProgress, aRequest) { if (!gYaSearchService.browserButtons.navigElements) return; let url = this._getUrlFromLocation(aRequest.URI); if (!url) return; let cyDataToSet = { post: aRequest.requestMethod === "POST" }; let wpCurrentURI = aWebProgress.currentURI; if (aWebProgress.loadType & 0x800000 && wpCurrentURI && wpCurrentURI.spec && url != wpCurrentURI.spec) { cyDataToSet.original = this._getUrlFromLocation(aWebProgress.currentURI); cyDataToSet.referring = this._getUrlFromLocation(aWebProgress.referringURI); } gYaURLInfo.setCY(aRequest.URI, cyDataToSet); }, onPageStateStop: function(aWebProgress, aRequest) { if (!this._checkIsTopWindowRequested(aWebProgress, aRequest)) return; let url = this._getUrlFromLocation(aWebProgress.currentURI); if (!url) return; this._checkNeedRefreshData(url, gYaSearchService.browserButtons); if (!gYaSearchService.browserButtons.navigElements) return; let originalURL = this._getUrlFromLocation(aRequest.originalURI); try { if (originalURL == aRequest.URI.spec) originalURL = false; } catch(e) {} gYaSearchService.getCY(url, aWebProgress, false, originalURL, this._getDataSumm(aWebProgress)); } }, confirmCYSpam: function(aUrl, aElement) { this.xmlHttpRequest(this.appendStatData2Url(aUrl,{}), { callbackFunc: this.confirmedCYSpam.bind(this, aUrl, aElement) }); }, confirmedCYSpam: function(aReq, aUrl, aElement) { let browser; if (aElement && aElement.localName) { if ("menuitem" == aElement.localName) aElement = aElement.parentNode.parentNode; if ("toolbarbutton" == aElement.localName && aElement.hasAttribute("oncommand")) browser = aElement.ownerDocument.defaultView; } if (!browser) return; if (this.isReqError(aReq)) { browser.alert(this.getString("spamError")); } else { var url = browser.gBrowser.selectedBrowser.currentURI.spec; if (url && url.length > 9 && aElement.getAttribute("oncommand") .indexOf("('http://bar-compl.yandex.ru/c?url=" + encodeURIComponent(url)) > 0) { let cy = gYaURLInfo.getCY(url); if (cy) cy.spam = false; aElement.disabled = true; } } }, getCY: function(aURL, aWebProgress, aFromCache, aOriginalURL, aDataSumm) { let cy = gYaURLInfo.setCY(aURL); let bloggers = gYaURLInfo.setBloggers(aURL); aURL = aURL || "undefined"; var originalURL = null; if (cy && cy.spam === null) { originalURL = aOriginalURL || cy.original || false; var referrer = aWebProgress.referringURI ? aWebProgress.referringURI.spec : (originalURL ? cy.referrer : null); cy.spam = (aURL == "undefined") ? false : "http://bar-compl.yandex.ru/c?url=" + encodeURIComponent(aURL) + (referrer ? ("&referer=" + encodeURIComponent(referrer)) : "") + (originalURL ? "&oldurl=" + encodeURIComponent(originalURL) : "") + "&login=" + (encodeURIComponent(this.username || "")); } let browser = aWebProgress.chromeEventHandler; this.setCY(false, browser, aURL); if (!cy || (aFromCache && aWebProgress.isLoadingDocument)) return; let urlinfo = 0; if (this.browserButtons.cy) { urlinfo |= 1; } if (this.browserButtons.bloggers) { urlinfo |= 2; } if (!urlinfo) return; if ( !!((urlinfo & 1) && (cy.state & gYaURLInfo.CY_STATE_UNKNOWN)) || !!((urlinfo & 2) && (bloggers.buttonState & gYaURLInfo.BLOGGERS_STATE_UNKNOWN)) || !!(aDataSumm && (aDataSumm.time || aDataSumm.action))) { if (urlinfo & 1) cy.state = gYaURLInfo.CY_STATE_REQUEST; if (urlinfo & 2) bloggers.buttonState = gYaURLInfo.BLOGGERS_STATE_REQUEST; originalURL = originalURL || aOriginalURL || cy.original || false; var post = cy.post;//this.cachedCYsPosts[aURL] || this.cachedCYsPosts[originalURL] || false; let tSumm = ""; if (aDataSumm) { if (aDataSumm.time) { tSumm += "&tv=" + aDataSumm.time.tv + "&t=" + aDataSumm.time.t; if (aDataSumm.time.yamm) tSumm += "&yamm=" + encodeURIComponent(aDataSumm.time.yamm); } if (aDataSumm.action) tSumm += "&action=" + aDataSumm.action; if (aDataSumm.httpStatus) tSumm += "&httpstatus=" + aDataSumm.httpStatus; } let ui = this.guidString; if (ui) { ui = "&ui=" + encodeURIComponent(ui.replace(/^\{/, "").replace(/\}$/, "")); let r1 = this.barnavigR1String; if (r1) ui += "&r1=" + encodeURIComponent(r1); } let params = ["ver=" + this.barExtensionVersionWithLocale + tSumm + "&" + this.getAppendStatData2Url({clid:4}) + (ui || "") + "&urlinfo=" + urlinfo + "&url=" + encodeURIComponent(aURL) + "&show=1&post=" + (post ? 1 : 0) + (aWebProgress.referringURI && aWebProgress.referringURI.userPass == "" ? "&referer=" + encodeURIComponent(aWebProgress.referringURI.spec) : "") + (originalURL ? "&oldurl=" + encodeURIComponent(originalURL) : ""), "",//hip (browser.contentTitle ? ("&title=" + encodeURIComponent(("" + browser.contentTitle).substr(0,1000))) : "") ]; gYaURLInfo.asyncGetIPsForURL(aURL, this.sendCY.bind(this, params, browser, aURL, urlinfo)); } }, sendCY: function(aIPs, aParams, aBrowser, aURL, aUrlinfo) { if (aIPs) { aIPs.some(function(aIP) { let parts = aIP ? aIP.match(/^(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})$/) : null; if (!parts) return false; aParams[1] = "&hip=" + ((parts[1] * 16777216) + (parts[2] * 65536) + (parts[3] * 256) + (parts[4] * 1)); return true; }); } this.xmlHttpRequest("http://bar-navig.yandex.ru/u?" + aParams.join(""), { callbackFunc: this.setCY.bind(this, aBrowser, aURL, aUrlinfo) }); }, setCY: function(aReq, aBrowser, aURL, aUrlinfo, aDontResend) { let [cy, bloggers] = gYaURLInfo.getCYAndBloggers(aURL); let checkBloggers = false; if (aReq) { if (!(cy && bloggers)) { this.log("No CY or Bloggers data"); return; } if (this.isReqError(aReq)) { if (!aDontResend) { try { var reqURL = aReq.target.channel.name; var nameReg = /^(http:\/\/)(bar\-navig\.yandex\.ru)/; if (reqURL && nameReg.test(reqURL)) { var status = 0; try { status = parseInt(aReq.target.status, 10) || 0; } catch(ex) {} if (status != 200) { this.xmlHttpRequest(reqURL.replace(nameReg, "$1backup-$2") + "&pstatus=" + status, { callbackFunc: this.setCY.bind(this, aBrowser, aURL, aUrlinfo, true) }); return; } } } catch(e) {} } if (aUrlinfo & 1) cy.state = gYaURLInfo.CY_STATE_ERROR; if (aUrlinfo & 2) bloggers.buttonState = gYaURLInfo.BLOGGERS_STATE_ERROR; } else { this.checkNeedSendGuid(); let urlinfoXml = this.safeE4Xml(aReq.target.responseText, null, "urlinfo"); if (urlinfoXml) { if (aUrlinfo & 1) { cy.state = gYaURLInfo.CY_STATE_RESPONSE; const REGION_REG = new RegExp(UConverter.ConvertToUnicode("╨á╨╡╨│╨╕╨╛╨╜: (.*)"), "g"); const THEME_REG = new RegExp(UConverter.ConvertToUnicode("^\\s*╨ó╨╡╨╝╨░:\\s*"), ""); let cyData = {}; cyData.domain = urlinfoXml.url.@domain.toString(); cyData.value = parseInt(urlinfoXml.tcy.@value.toString(), 10) || 0; cyData.rang = parseInt(urlinfoXml.tcy.@rang.toString(), 10) || 0; let titles = []; for each (let topic in urlinfoXml.topics.topic) { let title = topic.@title.toString().replace(THEME_REG, ""); if (title) titles.push(title); } cyData.theme = titles.length ? titles.join(", ") : this.getString("cyNoTheme"); let region = REGION_REG.exec(urlinfoXml.textinfo.toString()); cyData.region = (region && region[1]) ? region[1] : this.getString("cyNoRegion"); if (urlinfoXml.r1.length() == 1) { let r1 = urlinfoXml.r1.toString(); if (r1) { this.barnavigR1String = r1; } } gYaURLInfo.setCY(aURL, cyData); } if (aUrlinfo & 2) { if ((bloggers.buttonState & gYaURLInfo.BLOGGERS_STATE_REQUEST) || urlinfoXml.page.length() == 1) { bloggers.value = parseInt(urlinfoXml.page.@count, 10) || 0; if (bloggers.value) checkBloggers = true; } bloggers.buttonState = gYaURLInfo.BLOGGERS_STATE_RESPONSE; } } else { if (aUrlinfo & 1) cy.state = gYaURLInfo.CY_STATE_ERROR; if (aUrlinfo & 2) bloggers.buttonState = gYaURLInfo.BLOGGERS_STATE_ERROR; } } } try { var browser = aBrowser.boxObject.element.ownerDocument.defaultView; if (aBrowser == browser.gBrowser.selectedBrowser && ((aURL == "undefined") || (aBrowser.webProgress.currentURI.spec == aURL))) { if (!aUrlinfo || (aUrlinfo & 1)) browser.Ya.setCY(cy); if (!aUrlinfo || (aUrlinfo & 2)) browser.Ya.Bloggers.setData(bloggers, checkBloggers); } } catch(e) {} }, refreshCYInAllBrowsers: function() { this.browserButtons = null; gYaURLInfo.clear(); for each (let browser in this.getWindows("navigator:browser")) { try { var yaButtons = browser.Ya.buttonsObject; var webProgress = browser.gBrowser.selectedBrowser.webProgress; webProgress.QueryInterface(Ci.nsIWebNavigation); webProgress.QueryInterface(Ci.nsIDocShell); var me = this; new G_Timer(function() { me.webProgressListener.onLocationChange(webProgress, yaButtons); }, 0); } catch(e) {} } }, getWindow: function(aWindowType) { return this.windowMediator.getMostRecentWindow(aWindowType); }, getWindows: function(aWindowType) { let windows = [], enumerator = this.windowMediator.getEnumerator(aWindowType); while (enumerator.hasMoreElements()) windows.push(enumerator.getNext()); return windows; }, get passwordManager() { return Cc["@mozilla.org/autocomplete/search;1?name=YasearchPassComplete"].getService().wrappedJSObject; }, getInstallDir: function() { return Cc["@mozilla.org/extensions/manager;1"] .getService(Ci.nsIExtensionManager) .getInstallLocation(EXT_ID) .getItemLocation(EXT_ID); }, getChromeDir: function() { var file = this.getInstallDir(); file.append("chrome"); return file; }, getContentDir: function() { var file = this.getChromeDir(); file.append("content"); return file; }, getYandexDir: function() { var file = Cc["@mozilla.org/file/directory_service;1"].getService(Ci.nsIProperties).get("ProfD", Ci.nsIFile); file.append(this.settingsFolderName); if (!file.exists()) file.create(Ci.nsIFile.DIRECTORY_TYPE, 0755); if (!file.exists()) throw "Can't create '" + this.settingsFolderName + "' folder in profile"; return file; }, getServicesDataFile: function() { if (!this.xmlServicesFile) { var file = this.getContentDir(); file.append("services"); file.append(this.xmlServicesFileName); if (!file.exists()) throw this.xmlServicesFileName + " is missing"; if (!file.isFile() || !file.isReadable()) throw this.xmlServicesFileName + " has type or permission problems"; this.xmlServicesFile = file; } return this.xmlServicesFile; }, getServicesData: function() { return this.readFile(this.getServicesDataFile()); }, getUserDataFile: function() { var file = this.getYandexDir(); file.append(this.xmlServicesFileName); if (!file.exists() || !file.isFile()) file.create(Ci.nsIFile.NORMAL_FILE_TYPE, 0755); if (!file.exists() || !file.isFile()) throw "Can't create '" + this.xmlServicesFileName + "' in profile"; if (!file.isReadable()) throw this.xmlServicesFileName + " has type or permission problems"; return file; }, refreshXmlServices: function() { if (this._xmlServices) { this._xmlServices = null; OBSERVER_SERVICE.notifyObservers(null, "Ya-Refresh-Data", "services"); } }, get xmlServices() { if (!this._xmlServices) { this._xmlServices = this.domParser.parseFromString(this.getServicesData(), "text/xml"); this.appendUserSessionData("services"); } return this._xmlServices; }, appendUserSessionData: function(aType) { var userDataFile = this.getUserDataFile(); if (!userDataFile) return; try { var userData = new XML(this.readFile(userDataFile)); } catch(e) { return; } switch (aType) { case "services": let desktop = this.getServiceById("desktop"); if (desktop && !this.isYandeskInstalled) desktop.removeAttribute("search-url"); var timeNow = G_TIME_NOW; for each (var serv in userData.timestamps.serv) { let elem = this.getServiceById(serv.@id); if (elem) elem.setAttribute("service-timestamp", timeNow--); } break; case "data": for each (var user in userData.users.user) { if (user.@login && user.@login.toString() > "") { let login = user.@login.toString(); if ("undefined" == typeof this.usersData[login]) this.usersData[login] = {}; this.usersData[login]._mailLastMaxId = user.mail.@last.toString().replace(/\D/g, "") || "0"; this.usersData[login]._mailPermCounter = this.parseIntFromStr(user.mail.@counter.toString()); this.Counters.appendUserSessionData(login, user.counters, user.yaru); this.usersData[login]._guidLastMsgTs = user.guid.@message_ts.toString().replace(/\D/g, ""); this.usersData[login]._bookmarksRawXml = this.safeE4Xml(user.bookmarks.toString(), "<page><bookmarks/></page>", "page"); } } break; default: break; } }, flushUserData: function() { if (!(this.xmlServices && this.xmlServices.documentElement)) return; var userDataFile = this.getUserDataFile(); if (userDataFile && userDataFile.isWritable()) { var userData = new XML('<data><version value="' + this.version + '"/><timestamps/><users/><lastengine/></data>'); let xpathStr = "//xul:toolbarbutton/xul:menupopup/xul:menuitem[starts-with(@id,'yasearchMenuIdPrefix-')]"; let elems = this.xPathEvaluator.evaluate(xpathStr, this.getDOMDocContent("bar-services"), function() { return XULNS; }, this.orSnapshotType, null); for (let i = 0, obj; (obj = elems.snapshotItem(i)); i++) { let len = userData.timestamps.serv.length(); let serv = userData.timestamps.serv[len] = <serv/>; serv.@id = obj.getAttribute("id").split("yasearchMenuIdPrefix-")[1]; } for (var data in this.usersData) { let len = userData.users.user.length(); let user = userData.users.user[len] = <user/>; user.@login = data; user.mail = <mail/>; if (this.usersData[data]._mailLastMaxId > "0") user.mail.@last = this.usersData[data]._mailLastMaxId; if (this.usersData[data]._mailPermCounter > 0) user.mail.@counter = this.usersData[data]._mailPermCounter; if (this.usersData[data]._guidLastMsgTs > "") { user.guid = <guid/>; user.guid.@message_ts = this.usersData[data]._guidLastMsgTs; } if (this.usersData[data]._bookmarksRawXml) { user.bookmarks = <bookmarks/>; user.bookmarks = this.usersData[data]._bookmarksRawXml.toString(); } //~ user.counters = this.Counters.getUserSessionDataForFlush(data); var [countersData, yaruData] = this.Counters.getUserSessionDataForFlush(data); user.counters = countersData; user.yaru = yaruData; } this.writeFile(userDataFile, userData); } }, getXSLTemplate: function(fName) { if (!this._xsltemplates[fName]) { let fullName = "xsl-" + fName + ".xsl"; let file = this.getContentDir(); file.append("xsl-templ"); file.append(fullName); if (!file.exists()) throw "getXSLTemplate -- " + fullName + " is missing"; let content = this.readFile(file); let include = this.xsltImportRegExp.exec(content); if (include && include[1]) { include = this.getInludeXSLTemplate(include[1]); content = content.replace(this.xsltImportRegExp, include); } this._xsltemplates[fName] = this.domParser.parseFromString(content, "text/xml"); } return this._xsltemplates[fName]; }, getLocaleFile: function(aFileName) { let file = this.getInstallDir(); ["chrome", "locale", "en-US"] .concat(aFileName.split("/")) .forEach(function(p) { file.append(p); }); return file; }, getInludeXSLTemplate: function(fName) { var incHashName = "include-" + fName; if (!this._xsltemplates[incHashName]) { var content = this.xmlSerializer.serializeToString(this.getXSLTemplate(fName)); content = content.split("<xsl:output method=\"xml\" encoding=\"UTF-8\" indent=\"no\"/>")[1]; content = content.split("</xsl:stylesheet>")[0]; this._xsltemplates[incHashName] = content; } return this._xsltemplates[incHashName]; }, getDOMDocContent: function(xslName, aDataSource) { if (aDataSource && aDataSource.firstChild.localName == "parsererror") return null; const xsltProcessor = Cc["@mozilla.org/document-transformer;1?type=xslt"].createInstance(Ci.nsIXSLTProcessor); xsltProcessor.setParameter(null, "localeTld", this.localeTld); xsltProcessor.importStylesheet(this.getXSLTemplate(xslName)); return xsltProcessor.transformToDocument(aDataSource || this.xmlServices).firstChild; }, getDOMDocContent2: function(xslFilePath, aDataSource, aParameters) { switch (typeof aDataSource) { case "string"://filepath aDataSource = this.getXSLTemplate2(aDataSource); break; case "xml": aDataSource = this.domParser.parseFromString(aDataSource, "text/xml"); if (aDataSource.firstChild.localName == "parsererror") return null;//throw new Error("getDOMDocContent2: not valid xml"); break; default: break; } let parameters = aParameters || {}; if (!("localeTld" in parameters)) parameters.localeTld = this.localeTld; const xsltProcessor = Cc["@mozilla.org/document-transformer;1?type=xslt"].createInstance(Ci.nsIXSLTProcessor); for (let [paramName, paramValue] in Iterator(parameters)) xsltProcessor.setParameter(null, paramName, paramValue); xsltProcessor.importStylesheet(this.getXSLTemplate2(xslFilePath)); //if (aDocument) //return xsltProcessor.transformToFragment(aDataSource, aDocument); return xsltProcessor.transformToDocument(aDataSource).firstChild; }, getXSLTemplate2: function(aFilePath) { var file = this.getContentDir(); aFilePath.split("/").forEach(function(fpath) { file.append(fpath); }); if (!file.exists()) throw new Error("getXSLTemplate2 -- " + aFilePath + " is missing"); return this.domParser.parseFromString(this.readFile(file), "text/xml"); }, getServiceById: function(id) { function nsResolver() { return "urn:data"; } let elem = this.xPathEvaluator.evaluate("//xmlns:*[@id='" + id + "']", this.xmlServices.documentElement, nsResolver, this.unSnapshotType, null); return elem && elem.snapshotLength ? elem.snapshotItem(0) : null; }, setServiceTimestamp: function(id) { let elem = this.getServiceById(id); if (!elem) return null; elem.setAttribute("service-timestamp", G_TIME_NOW); OBSERVER_SERVICE.notifyObservers(null, "Ya-Refresh-Services", false); return elem; }, getDefaultSearchEngine: function() { function nsResolver() { return "urn:data"; } let elem = this.xPathEvaluator.evaluate("//xmlns:*[@search-url]", this.xmlServices.documentElement, nsResolver, this.unSnapshotType, null); return elem && elem.snapshotLength ? elem.snapshotItem(0).getAttribute("id") : null; }, get searchService() { if (!this._searchService) this._searchService = Cc["@mozilla.org/browser/search-service;1"].getService(Ci.nsIBrowserSearchService); return this._searchService; }, get searchEngineSuggestURL() { return this._searchEngineSuggestURL || (this._searchEngineSuggestURL = "http://suggest.yandex." + this.localeTld + "/suggest-ff.cgi?part="); }, //see nsIYaSearchSuggestions get defaultYandexSearchEngine() { return { _self: this, supportsResponseType: function(aType) { return aType == "application/x-suggestions+json"; }, getSubmission: function(aData, aResponseType) { return { postData: null, uri: this._self.makeURI(this._self.searchEngineSuggestURL + encodeURIComponent(aData)) } } }; }, get currentSearchEngine() { if (!this._yaCurrentEngine.isYandex) return this.searchService.getEngineByName(this._yaCurrentEngine.name); return { _self: this, _currentEngine: this._yaCurrentEngine, name: "___ya___" + this._yaCurrentEngine.name, supportsResponseType: function(aType) { return aType == "application/x-suggestions+json"; }, getSubmission: function(aData, aResponseType) { return { postData: null, uri: this._self.makeURI(this._self.searchEngineSuggestURL + encodeURIComponent(aData)) } } }; }, desktopPinger: { checkService: function() { if (this._desktopServicePath) { var req = Cc["@mozilla.org/xmlextras/xmlhttprequest;1"].createInstance(Ci.nsIXMLHttpRequest); req.open("HEAD", this._desktopServicePath); var target = req.QueryInterface(Ci.nsIDOMEventTarget); if (this.__triesCount) {//not first time target.addEventListener("load", this._reloadSearchErrorPages.bind(this), false); target.addEventListener("error", this._startTimer.bind(this), false); } else { target.addEventListener("error", this._pingDesktopServiceCallback.bind(this), false); } try { req.send(null); } catch(e) {} } }, __timer: null, __triesCount: 0, _reloadSearchErrorPages: function() { this._stop(true); var desktopServicePath = this._desktopServicePath; new G_Timer(function() { for each (var browser in gYaSearchService.getWindows("navigator:browser")) { var browserInstance = browser.getBrowser(); var numTabs = browserInstance.tabContainer.childNodes.length; for (var index = 0; index < numTabs; index++) { var currentBrowser = browserInstance.getBrowserAtIndex(index); if (desktopServicePath == currentBrowser.currentURI.prePath && /^about\:neterror/.test(currentBrowser.contentDocument.documentURI) && !currentBrowser.hasAttribute("busy")) { currentBrowser.loadURI(currentBrowser.currentURI.spec); } } } }, 3000); }, _stop: function(aDropCounter) { if (this.__timer) this.__timer.cancel(); this.__timer = null; if (aDropCounter) this.__triesCount = 0; }, _startTimer: function() { if (this.__triesCount++ < 10) { this._stop(); this.__timer = new G_Timer(this.checkService.bind(this, true), 1000); } else { this._stop(true); } }, __desktopServicePath: null, get _desktopServicePath() { if (this.__desktopServicePath === null) { this.__desktopServicePath = false; var desktopService = gYaSearchService.getServiceById("desktop"); if (desktopService && desktopService.hasAttribute("search-url")) { var uri = gYaSearchService.makeURI(desktopService.getAttribute("search-url")); if (uri) this.__desktopServicePath = uri.prePath; } } return this.__desktopServicePath; }, _pingDesktopServiceCallback: function(aReq) { var exePath = gYaSearchService.getYandeskProgramDir(); if (exePath) { var desctopExeFile = Cc["@mozilla.org/file/local;1"].createInstance(Ci.nsILocalFile); desctopExeFile.initWithPath(exePath); desctopExeFile.append("yandesk.exe"); if (desctopExeFile.exists() && desctopExeFile.isFile()) { desctopExeFile.launch(); this._startTimer(); } } } }, getSearchEngineUrl: function(aId, aText, aHost, aStatData) { var engine, result = { isYandexSearch: false }, id = aId.replace(/^__/, ""); if (id == aId) { result.isYandexSearch = true; engine = this.getServiceById(aId); if (engine) { if (aId === "desktop" && this.isYandeskInstalled) this.desktopPinger.checkService(); var appendix = aHost && engine.hasAttribute("search-site") ? "&" + engine.getAttribute("search-site") + "=" + encodeURIComponent(aHost) : ""; var searchURL = engine.getAttribute("search-url") + (encodeURIComponent(aText)) + appendix; result.url = this.appendStatData2Url(searchURL, (typeof aStatData == "undefined") ? {clid:2} : aStatData); var action = engine.hasAttribute("search-action") ? engine.getAttribute("search-action") : (engine.hasAttribute("action") ? engine.getAttribute("action") : null); result.statData = action ? {action: action} : null; result.postData = null; } } else { engine = this.searchService.getEngineByName(id); if (engine) { var submission = engine.getSubmission(aText, null); if (submission) { result.url = submission.uri.spec; result.statData = {action: "4300"}; result.postData = submission.postData; } } } return result.url ? result : null; }, setCurrentSearchEngine: function(aId) { var elem, result = {}, id = aId.replace(/^__/, ""); this._yaCurrentEngine = {isYandex: false, name: id}; if (id == aId) { this._yaCurrentEngine.isYandex = true; function nsResolver() { return "urn:data"; } var obj, elems = this.xPathEvaluator.evaluate("//xmlns:*[@last-engine]", this.xmlServices.documentElement, nsResolver, this.unSnapshotType, null); for (var i = 0; (obj = elems.snapshotItem(i)); i++) obj.removeAttribute("last-engine"); elem = this.getServiceById(aId); if (elem) { elem.setAttribute("last-engine", "true"); result.searchUrl = elem.getAttribute("search-url"); result.searchSite = elem.getAttribute("search-site"); result.label = elem.getAttribute("label2") || elem.getAttribute("label"); result.image = CHROME_IMAGES + elem.getAttribute("image") + ".png"; } } else { elem = this.searchService.getEngineByName(id); if (elem) { result.label = id; result.image = elem.iconURI ? elem.iconURI.spec : ""; result.searchUrl = elem.uri; } } return result.label ? result : null; }, getSearchSettingsForSlovari: function(aText, aEvent, aCallback) { this.xmlHttpRequest("http://export.yandex.ru/mycookie.xml", {callbackFunc: this.getSearchSettingsForSlovariCallback.bind(this, aText, aEvent, aCallback)}); }, getSearchSettingsForSlovariCallback: function(aReq, aText, aEvent, aCallback) { let type = "slovari-services"; if (!this.isReqError(aReq) && /<translate>1<\/translate>/.test(aReq.target.responseText)) type = "lingvo"; let engineData = this.getSearchEngineUrl(type, aText); aCallback(engineData.url, aEvent, engineData.statData); }, uninit: function() { if (this._inited) { this._inited = false; ["cookie-changed", "http-on-modify-request", "http-on-examine-response"] .forEach(function(aTopicName) { OBSERVER_SERVICE.removeObserver(this, aTopicName, true); }, this); this.cancelLogoutConnection(); this.clearAllTimers(); if (gYaInstaller && !gYaInstaller.isBarUninstalled) this.flushUserData(); //[2do] this._browserButtons = null; } this._searchService = null; }, handlePrefChanges: function(aData) { switch (aData.split("yasearch.")[1]) { case "general.debug.enabled": this.debug = this.getBoolPref(aData); break; case "general.ui.show.cy.value": this.refreshCYInAllBrowsers(); break; case "general.ui.urlbar.corrector.state": OBSERVER_SERVICE.notifyObservers(null, "Ya-Refresh-Data", "urlbar-corrector"); break; case "http.update.weathertraff.interval": this.updateHttpTimers("weathertraff"); break; case "http.update.interval": this.updateHttpTimers("mailandfeeds"); break; case "http.auto.enabled": this.updateHttpTimers(); break; case "general.ui.mail.integration": OBSERVER_SERVICE.notifyObservers(null, "Ya-Refresh-Data", "mail-integration"); break; } }, get isCountersAutoUpdateEnabled() { return this.getBoolPref("yasearch.http.auto.enabled"); }, updateHttpTimers: function(aTimerType) { var autoUpdateEnabled = this.isCountersAutoUpdateEnabled; if (!aTimerType || aTimerType == "weathertraff") { var time = autoUpdateEnabled ? (this.getIntPref("yasearch.http.update.weathertraff.interval") * MIN_SEC || 0) : 0; this.yaCity.updateObserversTime(time); } if (!aTimerType || aTimerType == "mailandfeeds") { this.checkTimeOut._MailAndFeeds = autoUpdateEnabled ? (this.getIntPref("yasearch.http.update.interval") * MIN_SEC || 0) : 0; this.isLogin && this.checkTimeOut._MailAndFeeds > 0 ? this.setTimer("_MailAndFeeds") : this.clearTimer("_MailAndFeeds"); } }, get barPref() { if (!this._barPref) this._barPref = " YB/" + this.barExtensionVersionWithLocale; return this._barPref; }, get barPrefReg() { if (!this._barPrefReg) this._barPrefReg = new RegExp(this.barPref.replace(/(\.|\-)/g, "\\\$1")); return this._barPrefReg; }, __localeTld: null, get localeTld() { if (!this.__localeTld) this.__localeTld = this.getString("locale.tld"); return this.__localeTld; }, isYandexHost: function(aHost) { return /(^|\.)(yandex\.(ru|ua|by|kz|net|com)|(ya|narod|moikrug)\.ru)$/i.test(aHost); }, _getDOMWindowForRequest: function(aRequest) { /* var loadContext; try { loadContext = aRequest.QueryInterface(Ci.nsIChannel).notificationCallbacks.getInterface(Ci.nsILoadContext); } catch(e) { try { loadContext = aRequest.loadGroup.notificationCallbacks.getInterface(Ci.nsILoadContext); } catch(ex) { loadContext = null; } } // loadContext.topWindow, loadContext.DOMWindow return loadContext ? loadContext.DOMWindow : null; */ try { return aRequest.loadGroup.groupObserver.QueryInterface(Ci.nsIWebProgress).DOMWindow; } catch(e) {} return null; }, _getTabForDOMWindow: function(aDOMWindow) { var tab = null; var docShellTree = aDOMWindow.QueryInterface(Ci.nsIInterfaceRequestor) .getInterface(Ci.nsIWebNavigation) .QueryInterface(Ci.nsIDocShellTreeItem); if (docShellTree.itemType == Ci.nsIDocShellTreeItem.typeContent) { try { var chromeWindow = docShellTree.rootTreeItem .QueryInterface(Ci.nsIInterfaceRequestor) .getInterface(Ci.nsIDOMWindow) .wrappedJSObject; if (!chromeWindow) return null; tab = chromeWindow.getBrowser() .getBrowserForDocument(aDOMWindow.document); if (!tab) return null; if (!tab.yaSearchTHandler) { var YaProgressListener = chromeWindow.YaProgressListener; if (YaProgressListener) YaProgressListener.addTabListener(tab); } if (tab.yaSearchTHandler) return tab; } catch(e) {} } return null; }, _getYaSearchTHandlerForRequest: function(aRequest) { var win = this._getDOMWindowForRequest(aRequest); if (win && win === win.parent) { var tab = this._getTabForDOMWindow(win); if (tab) return tab.yaSearchTHandler; } return null; }, observe: function(aSubject, aTopic, aData) { switch (aTopic) { case "http-on-modify-request": aSubject.QueryInterface(Ci.nsIHttpChannel); if (this.isYandexHost(aSubject.URI.host)) { try { var ua = aSubject.getRequestHeader("User-Agent"); if (!this.barPrefReg.test(ua)) aSubject.setRequestHeader("User-Agent", ua + this.barPref, false); } catch(e) {} } try { if (aSubject.loadFlags & Ci.nsIHttpChannel.LOAD_DOCUMENT_URI) { var tabHandler = this._getYaSearchTHandlerForRequest(aSubject); if (tabHandler) tabHandler.onTransferStart(aSubject.URI.spec); } } catch(e) {} break; case "http-on-examine-response": aSubject.QueryInterface(Ci.nsIHttpChannel); try { if (aSubject.loadFlags & Ci.nsIHttpChannel.LOAD_DOCUMENT_URI) { var tabHandler = this._getYaSearchTHandlerForRequest(aSubject); if (tabHandler) tabHandler.onTransferStop(); } } catch(e) {} break; case "cookie-changed": var rootDomain = this.yaRootDomain; if (rootDomain && aSubject && aSubject instanceof Ci.nsICookie && aSubject.host == rootDomain && aSubject.path == "/") { var name = aSubject.name; if (name == "Session_id" || name == "yandex_login") { var val = ""; try { val = aSubject.value.toString(); } catch(e) {} if (aData == "deleted" || !val) val = false; var needRecheckAuth = !!(aData == "changed" && !this.isLogin); this.session = { val: val, name: (name == "Session_id" ? "Id" : "Login") }; if (needRecheckAuth && (this.session.id || this.session.login)) this.setSessionFromCookies(false); } } break; case "nsPref:changed": this.handlePrefChanges(aData); break; case "profile-after-change": this.init(); if (this._inited) { let prefInternal = Cc["@mozilla.org/preferences-service;1"].getService(Ci.nsIPrefBranch2); prefInternal.addObserver("yasearch", this, true); } break; case "profile-before-change": if (this._inited) { let prefInternal = Cc["@mozilla.org/preferences-service;1"].getService(Ci.nsIPrefBranch2); prefInternal.removeObserver("yasearch", this, true); } this.uninit(); break; case "app-startup": OBSERVER_SERVICE.addObserver(this, "browser-ui-startup-complete", false); OBSERVER_SERVICE.addObserver(this, "sessionstore-windows-restored", false); ["profile-before-change", "profile-after-change", "quit-application"] .forEach(function(aTopicName) { OBSERVER_SERVICE.addObserver(this, aTopicName, true); }, this); break; case "browser-ui-startup-complete": OBSERVER_SERVICE.removeObserver(this, "browser-ui-startup-complete"); this.onBrowserUIStartupComplete(); break; case "sessionstore-windows-restored": OBSERVER_SERVICE.removeObserver(this, "sessionstore-windows-restored"); this.onSessionstoreWindowsRestored(); break; case "quit-application": //this.shutdown(); break; } }, loadUserSheet: function(aFile) { if (aFile && aFile.exists() && aFile.isFile() && aFile.isReadable()) { var sss = Cc["@mozilla.org/content/style-sheet-service;1"].getService(Ci.nsIStyleSheetService); var u = this.makeFileURI(aFile); if (sss.sheetRegistered(u, sss.USER_SHEET)) sss.unregisterSheet(u, sss.USER_SHEET); sss.loadAndRegisterSheet(u, sss.USER_SHEET); } }, hackKnownSkins: function() { var selectedSkin = this.getCharPref("extensions.lastSelectedSkin") || this.getCharPref("general.skins.selectedSkin"); if (selectedSkin) { if (selectedSkin == "classic/1.0") selectedSkin = "classic"; var cssFile = this.getChromeDir(); cssFile.append("skin"); cssFile.append("themes-hacks"); var platformCssFile, platformName = this.AppInfo.OS.platformName; if (platformName) { platformCssFile = cssFile.clone(); platformCssFile.append(platformName); } [cssFile, platformCssFile].forEach(function(cssFile) { if (cssFile) { try { cssFile.append(selectedSkin + ".css"); if (cssFile.exists() && cssFile.isFile()) this.loadUserSheet(cssFile); } catch(e) {} } }, this) } var extSheetsDir = this.getChromeDir(); extSheetsDir.append("skin"); extSheetsDir.append("extensions-hacks"); if (extSheetsDir.exists() && extSheetsDir.isDirectory()) { var em = Cc["@mozilla.org/extensions/manager;1"].getService(Ci.nsIExtensionManager); var extSheetsDirEnumerator = extSheetsDir.directoryEntries; while (extSheetsDirEnumerator.hasMoreElements()) { var entry = extSheetsDirEnumerator.getNext().QueryInterface(Ci.nsIFile); if (entry.isFile()) { var name = entry.leafName; if (/.\.css$/.test(name)) { var emItem = em.getItemForID(name.slice(0, -4)); if (emItem && emItem.type == Ci.nsIUpdateItem.TYPE_EXTENSION) this.loadUserSheet(entry); } } } } }, /** **************************************************************************************************** **/ parseIntFromStr: function(aStr) { var res = aStr ? parseInt(aStr.toString().replace(/\D/g,""), 10) : 0; return isNaN(res) ? 0 : res; }, safeUnicode: function(aString) { if (!/[^\r\n\x9\xA\xD\x20-\uD7FF\uE000-\uFFFD\u10000-\u10FFFF]/.test(aString)) return aString; return aString.replace(/[^\r\n\x9\xA\xD\x20-\uD7FF\uE000-\uFFFD\u10000-\u10FFFF]/g, ""); }, getStringBundle: function() { if (!this.stringBundle) { var strBundleService = Cc["@mozilla.org/intl/stringbundle;1"].createInstance(Ci.nsIStringBundleService); this.stringBundle = strBundleService.createBundle("chrome://yasearch/locale/yasearch.properties"); } return this.stringBundle; }, getString: function(aName) { return this.getStringBundle().GetStringFromName(aName); }, getFormattedString: function(aName, aStrArray) { return this.getStringBundle().formatStringFromName(aName, aStrArray, aStrArray.length); }, getFormattedStringL18End: function(aName, aStrArray) { var n = aStrArray[0], _cases = [2,0,1,1,1,2,2,2,2,2]; var l18End = aName + "L18End" + ((n%100>10)&&(n%100<20) ? 2 : _cases[n%10]); return this.getFormattedString(aName, aStrArray) + this.getString(l18End); }, __localeDependedStrBundleService: null, getLocaleDependedUrl: function(aUrl) { if (!this.__localeDependedStrBundleService) { var strBundleService = Cc["@mozilla.org/intl/stringbundle;1"].createInstance(Ci.nsIStringBundleService); this.__localeDependedStrBundleService = strBundleService.createBundle("chrome://yasearch/locale/links/links.properties"); } return this.__localeDependedStrBundleService.GetStringFromName(aUrl); }, /** **************************************************************************************************** **/ utils: { get G_Timer() { return G_Timer; } }, /** **************************************************************************************************** **/ writeFile: function(aFile, aData) { //if (!(aFile instanceof Ci.nsIFile && aFile.isWritable())) // return; try { var chunk = UConverter.ConvertFromUnicode(aData); var os = Cc["@mozilla.org/network/file-output-stream;1"].createInstance(Ci.nsIFileOutputStream); os.init(aFile, 0x02 | 0x08 | 0x20, 0755, 0); var result = os.write(chunk, chunk.length); os.close(); } catch(e) {} }, readFile: function(aFile) { var fileContents = ""; //if (aFile.exists() && aFile.isFile() && aFile.isReadable()) { var is = Cc["@mozilla.org/network/file-input-stream;1"].createInstance(Ci.nsIFileInputStream); is.init(aFile, 0x01, 0, is.CLOSE_ON_EOF); var sis = Cc["@mozilla.org/scriptableinputstream;1"].createInstance(Ci.nsIScriptableInputStream); sis.init(is); while(sis.available() > 0) fileContents += UConverter.ConvertToUnicode(sis.read(sis.available())); is.close(); sis.close(); //} return this.safeUnicode(fileContents); }, prefBranchInternal: Cc["@mozilla.org/preferences-service;1"].getService(Ci.nsIPrefBranch2), prefBranch: Cc["@mozilla.org/preferences-service;1"].getService(Ci.nsIPrefBranch), setBoolPref: function(aName, aValue) { this.prefBranch.setBoolPref(aName, aValue); }, getBoolPref: function(aName) { let rv = null; try { rv = this.prefBranch.getBoolPref(aName); } catch(e) {} return rv; }, setIntPref: function(aName, aValue) { this.prefBranch.setIntPref(aName, aValue); }, getIntPref: function(aName) { let rv = null; try { rv = this.prefBranch.getIntPref(aName); if (rv < 0) rv = 0; } catch(e) {} return rv; }, setCharPref: function(aName, aValue) { this.prefBranch.setCharPref(aName, aValue); }, getCharPref: function(aName) { let rv = null; try { rv = this.prefBranch.getCharPref(aName); } catch(e) {} return rv; }, getComplexValue: function(aName) { let rv = null; try { rv = this.prefBranch.getComplexValue(aName, Ci.nsIPrefLocalizedString).data; } catch(e) {} return rv; }, setComplexValue: function(aName, aValue) { try { let str = Cc["@mozilla.org/supports-string;1"].createInstance(Ci.nsISupportsString); str.data = aValue; this.prefBranch.setComplexValue(aName, Ci.nsISupportsString, str); } catch(e) {} }, /* deletePrefBranch: function(aName) { try { this.prefBranch.deleteBranch(aName); } catch(e) {} }, */ resetPrefBranch: function(aPrefBranchName) { if (!aPrefBranchName) return; if (!/\.$/.test(aPrefBranchName)) aPrefBranchName += "."; this.prefBranch.getChildList(aPrefBranchName, {}).forEach(function(aPrefName) { try { this.resetPref(aPrefName); } catch(e) {} }, this); }, resetPref: function(aPrefName) { try { this.prefBranch.clearUserPref(aPrefName); } catch(e) {} }, getBrowserHomePage: function() { let url; try { url = this.getComplexValue("browser.startup.homepage"); } catch(e) {} if (!url) { var SBS = Cc["@mozilla.org/intl/stringbundle;1"].getService(Ci.nsIStringBundleService); var configBundle = SBS.createBundle("resource:/browserconfig.properties"); url = configBundle.GetStringFromName("browser.startup.homepage"); } return url; }, setBrowserHomePage: function(aValue) { if (this.yaDefence) this.yaDefence.protectedHomepage = aValue; this.setComplexValue("browser.startup.homepage", aValue); }, getBrowserKeywordURL: function() { let url; try { url = this.getComplexValue("keyword.URL") || this.getCharPref("keyword.URL"); } catch(e) {} if (!url) { const SBS = Cc["@mozilla.org/intl/stringbundle;1"].getService(Ci.nsIStringBundleService); let configBundle = SBS.createBundle("chrome://browser-region/locale/region.properties"); url = configBundle.GetStringFromName("keyword.URL"); } return url; }, setBrowserKeywordURL: function(aValue) { this.setComplexValue("keyword.URL", aValue); }, get appOS() { var gApp = Cc["@mozilla.org/xre/app-info;1"].getService(Ci.nsIXULAppInfo).QueryInterface(Ci.nsIXULRuntime); return gApp.OS; }, get windowsOS() { return ("nsIWindowsRegKey" in Ci) ? true : false; }, getYandeskProgramDir: function() { return this.WinReg.read("HKCU", "Software\\Yandex\\Yandesk", "ProgramDir"); }, get isYandeskInstalled() { return !!this.getYandeskProgramDir(); }, getYaOnlineProgramDir: function() { return this.WinReg.read("HKCU", "Software\\Yandex\\Online", "ProgramDir"); }, get isYaOnlineInstalled() { return !!this.getYaOnlineProgramDir(); }, WinReg: { /* ************************************** * * HKCU eq. USER eq. CURRENT_USER eq. HKEY_CURRENT_USER * HKCR eq. ROOT eq. CLASSES_ROOT eq. HKEY_CLASSES_ROOT * HKLM eq. MACHINE eq. LOCAL_MACHINE eq. HKEY_LOCAL_MACHINE * ************************************** */ _convertName2Key: function(aKeyName) { aKeyName = aKeyName.replace(/^(HKEY_)/i, "").toUpperCase(); var keyNamesHash = { "CURRENT_USER": ["HKCU", "USER", "CURRENT_USER"], "CLASSES_ROOT": ["HKCR", "ROOT", "CLASSES_ROOT"], "LOCAL_MACHINE": ["HKLM", "MACHINE", "LOCAL_MACHINE"] }; var keyName; for (var kName in keyNamesHash) { if (keyNamesHash[kName].indexOf(aKeyName) !== -1) { keyName = kName; break; } } if (!keyName) throw new TypeError("nsIYaSearch.WinReg: wrong key name"); return Ci.nsIWindowsRegKey["ROOT_KEY_" + keyName]; }, _readValue: function(wrk, value) { if (wrk.hasValue(value)) { switch (wrk.getValueType(value)) { case wrk.TYPE_STRING: return wrk.readStringValue(value); case wrk.TYPE_BINARY: return wrk.readBinaryValue(value); case wrk.TYPE_INT: return wrk.readIntValue(value); case wrk.TYPE_INT64: return wrk.readInt64Value(value); default: break; } } // unknown type or has no value return null; }, _writeValue: function(wrk, name, value, type) { type = type.toLowerCase(); switch (type) { case "string": wrk.writeStringValue(name, value); break; case "binary": wrk.writeBinaryValue(name, value); break; case "int": wrk.writeIntValue(name, value); break; case "int64": wrk.writeInt64Value(name, value); break; default: throw new TypeError("nsIYaSearch.WinReg: wrong key type"); break; } }, _removeChildren: function(wrk) { for (var i = wrk.childCount - 1; i >= 0; i--) { var name = wrk.getChildName(i); var subkey = wrk.openChild(name, wrk.ACCESS_ALL); this._removeChildren(subkey); subkey.close(); wrk.removeChild(name); } }, _getWrk: function() { return Cc["@mozilla.org/windows-registry-key;1"].createInstance(Ci.nsIWindowsRegKey); }, read: function(aKey, aPath, aName) { var result = null; if (gYaSearchService.windowsOS) { var key = this._convertName2Key(aKey); var wrk = this._getWrk(); try { wrk.open(key, aPath, wrk.ACCESS_READ); result = this._readValue(wrk, aName); } catch(e) {} try { wrk.close(); } catch(e) {} } return result; }, write: function(aKey, aPath, aName, aValue, aValueType) { if (gYaSearchService.windowsOS) { var key = this._convertName2Key(aKey); var wrk = this._getWrk(); try { wrk.create(key, aPath, wrk.ACCESS_WRITE); this._writeValue(wrk, aName, aValue, aValueType); } catch(e) {} try { wrk.close(); } catch(e) {} } }, remove: function(aKey, aPath, aName) { /* if (gYaSearchService.windowsOS) { var key = this._convertName2Key(aKey); var wrk = this._getWrk(); try { wrk.open(key, aPath, wrk.ACCESS_ALL); if (typeof aName === "undefined") this._removeChildren(wrk); else wrk.removeChild(aName); } catch(e) {} try { wrk.close(); } catch(e) {} } */ } }, get barExtensionVersion() { if (!this._barExtensionVersion) this._barExtensionVersion = this.barExtensionMajorVersion + this.VERSION_BUILD; return this._barExtensionVersion; }, get barExtensionMajorVersion() { if (!this._barExtensionMajorVersion) this._barExtensionMajorVersion = Cc["@mozilla.org/extensions/manager;1"].getService(Ci.nsIExtensionManager).getItemForID(EXT_ID).version; return this._barExtensionMajorVersion; }, get barExtensionVersionWithLocale() { if (!this._barExtensionVersionWithLocale) this._barExtensionVersionWithLocale = this.barExtensionVersion + this.versionLocaleAppend; return this._barExtensionVersionWithLocale; }, get versionLocaleAppend() { var verLocaleAppend = this.getString("locale"); if (verLocaleAppend) verLocaleAppend = "-" + verLocaleAppend; return verLocaleAppend; }, get generateGUIDStatusURL() { if (!this._generateGUIDStatusURL) { try { var vendorURL = this.getCharPref("yasearch.vendor.guid.url"); var URIFixup = Cc["@mozilla.org/docshell/urifixup;1"].getService(Ci.nsIURIFixup); vendorURL = URIFixup.createFixupURI(vendorURL, Ci.nsIURIFixup.FIXUP_FLAG_NONE); if ((vendorURL.scheme == "http" || vendorURL.scheme == "https") && /yandex\.ru$/i.test(vendorURL.host)) { vendorURL = vendorURL.spec; vendorURL += /\?/.test(vendorURL) ? (/&$/.test(vendorURL) ? "" : "&") : "?"; this._generateGUIDStatusURL = vendorURL; } } catch (ex) {} if (!this._generateGUIDStatusURL) this._generateGUIDStatusURL = "http://soft.export.yandex.ru/status.xml?"; } return this._generateGUIDStatusURL; }, get generateGUID() { return Cc["@mozilla.org/uuid-generator;1"].createInstance(Ci.nsIUUIDGenerator).generateUUID(); }, getYaAppDir: function() { var appDir; if (this.AppBarType == "barffport") { appDir = this.getPortableDir(); } else { try { appDir = Cc["@mozilla.org/file/directory_service;1"] .getService(Ci.nsIProperties) .get(this.windowsOS ? "AppData" : "Home", Ci.nsIFile); } catch(e) {} } if (appDir && appDir.exists() && appDir.isDirectory()) { appDir.append(this.windowsOS ? "Yandex" : ".yandex"); if (!appDir.exists() || !appDir.isDirectory()) { try { appDir.create(Ci.nsIFile.DIRECTORY_TYPE, 0755); } catch(e) {} } if (appDir.exists() && appDir.isDirectory()) return appDir; } return false; }, getPortableDir: function() { let curProcDir, badStructure = true; try { curProcDir = Cc["@mozilla.org/file/directory_service;1"] .getService(Ci.nsIProperties) .get("CurProcD", Ci.nsIFile) .parent; badStructure = ["AppInfo", "DefaultData", "Firefox"].some(function(aDirName) { let dir = curProcDir.clone(); dir.append(aDirName); return !(dir.exists() && dir.isDirectory()); }); } catch(e) {} return badStructure ? null : curProcDir; }, _AppBarType: null, get AppBarType() { if (!this._AppBarType) { let prefName = "yasearch.general.app.bar.type"; let barType = this.getCharPref(prefName); switch (barType) { case "barff": case "barffport": break; default: barType = !!this.getPortableDir() ? "barffport" : "barff"; this.setCharPref(prefName, barType); break; } this._AppBarType = barType; } return this._AppBarType; }, get vendorFileName() { return "clids-" + this.AppBarType + ".xml"; }, getYaPrefsFile: function(aFileName, aCreate) { function _isFileExists(aFile) { return !!(aFile.exists() && aFile.isFile()); } var appDir = this.getYaAppDir(); if (appDir) { var file = appDir.clone(); file.append(aFileName); if (aFileName == this.vendorFileName && !_isFileExists(file)) { //barie app var venFile = appDir.clone(); venFile.append("clids-barie.xml"); if (_isFileExists(venFile)) { try { venFile.copyTo(appDir, aFileName); venFile.permissions = 0755; } catch(e) {} } if (!_isFileExists(file)) { //ven app venFile = appDir.clone(); venFile.append("vendor.xml"); if (_isFileExists(venFile)) { try { venFile.copyTo(appDir, aFileName); venFile.permissions = 0755; } catch(e) {} } if (!_isFileExists(file)) { //ven dist venFile = this.getContentDir(); venFile.append("services"); venFile.append("vendor.xml"); if (_isFileExists(venFile)) { try { venFile.copyTo(appDir, aFileName); venFile.permissions = 0755; } catch(e) {} } }//venapp }//barieapp } if (aCreate == true && !_isFileExists(file)) file.create(Ci.nsIFile.NORMAL_FILE_TYPE, 0755); if (_isFileExists(file) && file.isReadable()) return file; } return false; }, getGuidDataFromString: function(aGuidStr) { var guid = aGuidStr ? aGuidStr.toString() : false; return guid && /^\{[0-9a-f]{2,8}\-[0-9a-f]{2,4}\-[0-9a-f]{2,4}\-[0-9a-f]{1,4}\-[0-9a-f]{2,12}\}$/i.test(guid) ? guid : false; }, __guidString: null, get guidString() { if (this.__guidString === null) { var guidPrefName = "yasearch.guid.value", guidStr = "", uiFile = this.getYaPrefsFile("ui"); if (uiFile) { guidStr = this.getGuidDataFromString(this.readFile(uiFile)); } else { var uiWasCreated = false; var currentWinUser; if (this.AppBarType !== "barffport") { currentWinUser = this.WinReg.read("HKCU", "Software\\Microsoft\\Windows\\CurrentVersion\\Explorer", "Logon User Name"); if (currentWinUser) { uiWasCreated = !!this.WinReg.read("HKCU", "Software\\Yandex", "UICreated_" + currentWinUser); } } if (!uiWasCreated) { if (this.prefBranch.prefHasUserValue(guidPrefName)) { guidStr = this.getGuidDataFromString(this.getCharPref(guidPrefName)); } else { guidStr = this.generateGUID; this.setCharPref(guidPrefName, guidStr); } if (guidStr) { uiFile = this.getYaPrefsFile("ui", true); if (!uiFile || !uiFile.isWritable()) { guidStr = ""; } else { this.writeFile(uiFile, guidStr); if (currentWinUser) { this.WinReg.write("HKCU", "Software\\Yandex", "UICreated_" + currentWinUser, 1, "int"); } } } } } if (guidStr) this.setCharPref(guidPrefName, guidStr); else guidStr = ""; this.__guidString = "" + (guidStr || ""); } return this.__guidString; }, __barnavigR1String: null, get barnavigR1String() { if (this.__barnavigR1String === null) { let r1 = "", r1File = this.getYaPrefsFile("r1-barff", false); if (r1File) { r1 = this.readFile(r1File);//vldt } this.__barnavigR1String = r1 || ""; } return this.__barnavigR1String; }, set barnavigR1String(val) { if (val !== this.barnavigR1String) { let r1File = this.getYaPrefsFile("r1-barff", true); if (r1File) { this.writeFile(r1File, val); } this.__barnavigR1String = null; } return this.barnavigR1String; }, vendorDataMergeClids: function() { //refresh vendor data this.__vendorData = null; var installedFile = this.getYaPrefsFile(this.vendorFileName, false); if (!installedFile) return; try { installedFile.permissions = 0755; } catch(e) {} var installedXml = this.safeE4Xml(this.readFile(installedFile), null, "vendor"); if (!installedXml) { try { installedFile.remove(true); } catch(e) {} return; } var distribFile = this.getContentDir(); distribFile.append("services"); distribFile.append("vendor.xml"); if (!(distribFile.exists() && distribFile.isFile())) return; var distribXml = this.safeE4Xml(this.readFile(distribFile), null, "vendor"); if (!distribXml) return; var writeNewData = false; for each (var clid in distribXml.*.(/^clid\d+$/.test(function::name()))) { var clidName = clid.name(); var clidValue = this.parseIntFromStr(clid.toString()); if (clidValue > 0 && (installedXml[clidName].length() === 0 || !this.parseIntFromStr(installedXml[clidName].toString()))) { installedXml[clidName] = clidValue; writeNewData = true; } } if (writeNewData) { this.writeFile(installedFile, "<?xml version=\"1.0\" encoding=\"windows-1251\"?>\r\n" + installedXml.toXMLString()); } }, get vendorData() { if (!this.__vendorData) { var data = {}; var vendorFile = this.getYaPrefsFile(this.vendorFileName, false); var vendorXml = this.safeE4Xml(vendorFile ? this.readFile(vendorFile) : "", "<vendor/>", "vendor"); for (var i = 0; i <= 10; i++) { var clid = this.parseIntFromStr(vendorXml["clid" + i].toString()); data["clid" + i] = clid > 0 ? clid.toString().substr(0, 10) : false; } this.__vendorData = data; } return this.__vendorData; }, get yandexHomePageValue() { var clid5 = this.vendorData.clid5; return "http://www.yandex." + this.localeTld + "/" + (clid5 ? "?clid=" + clid5 : ""); }, isYandexHomePage: function(aHomepageURL) { let url = typeof aHomepageURL === "undefined" ? this.getBrowserHomePage() : aHomepageURL; return !!(url && (/^http:\/\/(www\.)?yandex\.(ru|ua)/i.test(url) || /^http:\/\/ru\.start3\.mozilla\.com\/firefox/.test(url)) ); }, setHomePageUrl: function(aOverrideYandex) { if (aOverrideYandex || !this.isYandexHomePage()) this.setBrowserHomePage(this.yandexHomePageValue); if (this.getIntPref("browser.startup.page") === 0) this.setIntPref("browser.startup.page", 1); }, _checkKeywordUrl: function() { if (this.getCharPref("app.distributor") != "yandex") return; let keywordURL = this.getBrowserKeywordURL(); if (!keywordURL || this.prefBranch.prefHasUserValue("keyword.URL")) return; this._setKeywordUrl(false); }, _setKeywordUrl: function(aSetEnabled) { let keywordURL = this.getBrowserKeywordURL(); if (!(/[&?]clid=/.test(keywordURL) && /^http:\/\/yandex\.ru\/yandsearch\?/.test(keywordURL))) { let urlParams = []; let clid9 = this.vendorData.clid9; if (clid9) urlParams.push("clid=" + clid9); urlParams.push("yasoft=" + encodeURIComponent(this.AppInfo.yasoftStr)); urlParams.push("text="); this.setBrowserKeywordURL("http://yandex.ru/yandsearch?" + urlParams.join("&")); } if (aSetEnabled) this.setBoolPref("keyword.enabled", true); }, appendStatData2Url: function(aURL, aStatData) { if (!aStatData || typeof(aStatData) !== "object" || !aURL) return aURL; if (/[&?]yasoft=/.test(aURL)) aStatData.yasoft = false; if (/[&?]clid=/.test(aURL)) aStatData.clid = false; let appendix = this.getAppendStatData2Url(aStatData); if (appendix == "") return aURL; let url = aURL.split("?"); url = url[0] + "?" + appendix + (url[1] ? "&" + url[1] : ""); return url; }, getAppendStatData2Url: function(aStatData) { let res = []; if (aStatData && !(aStatData.action && !(aStatData.yasoft || aStatData.clid))) { if (aStatData.clid) { let clid = this.vendorData["clid" + (aStatData.clid || "")]; if (clid) res.push("clid=" + clid); } if ((aStatData.yasoft || null) !== false) res.push("yasoft=" + encodeURIComponent(this.AppInfo.yasoftStr)); } return res.join("&"); }, get versionData() { var gApp = Cc["@mozilla.org/xre/app-info;1"].getService(Ci.nsIXULAppInfo).QueryInterface(Ci.nsIXULRuntime); var versionData = { ui: this.guidString, v: this.barExtensionVersionWithLocale, ver: this.barExtensionVersionWithLocale, bn: gApp.name, bv: gApp.version, os: gApp.OS, yasoft: this.AppInfo.yasoftStr, tl: this.timeGuid }; if (this.vendorData.clid1) versionData.clid = this.vendorData.clid1; return versionData; }, get generateGUIDData() { if (!this._generateGUIDData) { var versionData = this.versionData; var data2Server = []; for (let [propName, propValue] in Iterator(versionData)) data2Server.push(propName + "=" + encodeURIComponent(propValue)); this._generateGUIDData = data2Server.join("&"); } var dynamicAppend = ""; if (this.yaDefence) { var yaDefenceTimesData = this.yaDefence.changesTime; if (yaDefenceTimesData) dynamicAppend += yaDefenceTimesData; var yaFSearchData = this.yaDefence.fSearchStatData; if (yaFSearchData) dynamicAppend += yaFSearchData; } var _use = "&stat=dayuse"; if (typeof(gYaInstaller) === "object" && "sttInstall" in gYaInstaller) { let stt = gYaInstaller.sttInstall; if (stt) _use = "&stat=install"; } dynamicAppend += _use; return this._generateGUIDData + dynamicAppend; }, __AppInfo: null, get AppInfo() { if (!this.__AppInfo) { var gApp = Cc["@mozilla.org/xre/app-info;1"].getService(Ci.nsIXULAppInfo).QueryInterface(Ci.nsIXULRuntime); var os = gApp.OS; var verLocaleAppend = this.getString("locale"); verLocaleAppend = verLocaleAppend ? ("." + verLocaleAppend) : ""; this.__AppInfo = { yasoftStr: "barff" + verLocaleAppend, OS: { name: os, isWindows: /^win/i.test(os), isLinux: /^linux/i.test(os), isMacOS: /^darwin/i.test(os), get platformName() { if (this.isWindows) return "win"; if (this.isLinux) return "unix"; if (this.isMacOS) return "mac"; return ""; } }, browser: { version: gApp.version, get isGreaterThenFx30() { return !!Ci.nsIWorker; }, get isGreaterThenFx35() { return !!Ci.nsIDOMGeoPositionAddress; } } }; } return this.__AppInfo; }, get timeGuid() { return (new Date(parseInt(this.getCharPref("yasearch.guid.time"), 10))).valueOf() || 0; }, set timeGuid(val) { this.setCharPref("yasearch.guid.time", val ? G_TIME_NOW : "0"); }, checkNeedSendGuid: function() { if (this.updateTimer._GuidRefresh) return; var timeNow = G_TIME_NOW, timeBefore = this.timeGuid; if (timeBefore < (timeNow - DAY_SECS) || timeBefore > timeNow) this.setTimer("_Guid", 10); this.setTimer("_GuidRefresh"); }, loadURI: function(aURL, aEvent, aClidType) { let browser = this.getWindow("navigator:browser"); return (browser && browser.Ya) ? browser.Ya.loadURI(aURL, aEvent, aClidType) : false; }, loadConditionalURI: function(aType, aEvent, aStatData) { let browser = this.getWindow("navigator:browser"); return (browser && browser.Ya) ? browser.Ya.loadConditionalURI(aType, aEvent, aStatData) : false; }, makeURI: function(aURLSpec, aCharset) { try { return IO_SERVICE.newURI(aURLSpec, aCharset, null); } catch(e) {} return null; }, makeFileURI: function(aFile) { try { return IO_SERVICE.newFileURI(aFile); } catch(e) {} return null; }, safeE4Xml: function(aStr, aDefaultStr, aRootNodeName) {//aRootNodeName -- null || string || array if (aStr) { if (typeof aStr == "string") { aStr = this.safeUnicode(aStr); } else { if (aStr instanceof Ci.nsIDOMDocument || aStr instanceof Ci.nsIDOMElement)//nsIDOMNode || nsIDOM3Node aStr = this.xmlSerializer.serializeToString(aStr); else if (typeof(aStr) === "xml") aStr = aStr.toString(); } } if (!aStr || aStr == "") aStr = (aDefaultStr || "").toString(); if (typeof(aStr) != "string") return null; aStr = aStr.replace(/<\?xml .+\?>[\r\n]*/, "") .replace(/(<!DOCTYPE ((.|\r|\n)*?)\]>)[\r\n]*/, ""); var d, rootNodeName; try { d = new XML(aStr)[0]; rootNodeName = d.name().localName.toString(); } catch(e) { this.log("'safeE4Xml' error: " + e); } if (d && rootNodeName) { if (!aRootNodeName) aRootNodeName = rootNodeName; var namesArray = typeof(aRootNodeName) == "string" ? [aRootNodeName] : aRootNodeName; if (namesArray.length > 0) for each (var name in namesArray) if (name == rootNodeName) return d; } return aDefaultStr ? this.safeE4Xml(aDefaultStr) : null; }, DOMUtils: { evaluateXPath: function(aNode, aExpr) { function nsResolver(aPrefix) { const ns = { "xul": "http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul", "xhtml": "http://www.w3.org/1999/xhtml" }; return ns[aPrefix] || null; } let xpEvaluator = Cc["@mozilla.org/dom/xpath-evaluator;1"].getService(Ci.nsIDOMXPathEvaluator); let xpathResult = xpEvaluator.evaluate(aExpr, aNode, nsResolver, Ci.nsIDOMXPathResult.UNORDERED_NODE_ITERATOR_TYPE, null); let nextElement, result = []; while ((nextElement = xpathResult.iterateNext())) result.push(nextElement); return result; }, // import - copy; adopt - remove importAndRemoveNode: function(aNode, aDocument) { if (!aNode) return aNode; var node = aDocument.importNode(aNode, true); try { aNode.parentNode.removeChild(aNode); } catch(e) {} return node; }, adoptNode: function(aNode, aDocument) { return this.importAndRemoveNode(aNode, aDocument); }, appendNode: function(aNode, aTarget) { var node = this.importAndRemoveNode(aNode, aTarget.ownerDocument); if (node) aTarget.appendChild(node); return node; }, replaceNode: function(aNewNode, aOldNode) { var fromDoc = aNewNode.ownerDocument, toDoc = aOldNode.ownerDocument; var node = (fromDoc === toDoc) ? aNewNode : this.importAndRemoveNode(aNewNode, toDoc); if (node) aOldNode.parentNode.replaceChild(node, aOldNode); return node; }, replaceChildNodes: function(aNode, aTarget) { while (aTarget.hasChildNodes()) aTarget.removeChild(aTarget.firstChild); return aNode ? this.appendNode(aNode, aTarget) : null; } }, /** **************************************************************************************************** **/ dumpIFaces: function(aObject) { if (!this.debug) return; var dumpTxt = ["Dump interfaces\r\n==============================================="]; for (var iface in Ci) { try { aObject.QueryInterface(Ci[iface]) dumpTxt.push(iface); } catch(e) {} } this.log(dumpTxt.join("\r\n")); return aObject; }, dump: function(aObject) { if (!this.debug) return; var dumpTxt = ["Dump properties in Object\r\n==============================================="]; for (var prop in aObject) try { dumpTxt.push(prop + " :: " + aObject[prop]); } catch(e) {} if (aObject instanceof Ci.nsIDOMEvent) { dumpTxt.push("================= nsIDOMEvent targets ======================================"); ["target", "currentTarget", "originalTarget", "explicitOriginalTarget"].forEach(function(aType) { dumpTxt.push(aType + " :: " + aObject[aType] + " :: " + (aObject[aType] ? aObject[aType].localName : null)) }) } this.log(dumpTxt.join("\r\n")); }, /** **************************************************************************************************** **/ _getToolbarForNode: function(aNode) { let toolbar = false, node = aNode; while (node && !toolbar) { node = node.parentNode; if (node && node.localName == "toolbar") toolbar = node; } return toolbar; }, _persistToolbarSet: function(aToolbar) { if (aToolbar && aToolbar.localName && aToolbar.localName == "toolbar") { aToolbar.setAttribute("currentset", aToolbar.currentSet); aToolbar.ownerDocument.persist(aToolbar.id, "currentset"); } }, checkToolbarSet: function(aNmb, aToolbar) { if (aNmb == this.barExtensionVersion) return; aToolbar.setAttribute("yaNmbSaved", this.barExtensionMajorVersion); aToolbar.ownerDocument.persist(aToolbar.id, "yaNmbSaved"); if (!aNmb) return; let gDocument = aToolbar.ownerDocument, defaultSet = aToolbar.getAttribute("defaultset"); let addDiff = { "3.5.0": [ ["yasearch-fotki", ",yasearch-mail", true], ["yasearch-yaru", ",yasearch-lenta", false] ], "4.0.0": [ ["yasearch-spellchecker", ",yasearch-bloggers", true] ], "4.3.0": [ ["yasearch-translate", ",yasearch-spellchecker", true] ] }; for (var nmb in addDiff) { if (aNmb <= nmb) { let i = -1, _d = addDiff[nmb]; while (_d[++i]) { let beforeElt = null; if (_d[i][1]) { let defSetCute = (defaultSet.split(_d[i][1])[0] + _d[i][1]).split(","), j = defSetCute.length; let found = false; while (defSetCute[--j] && !found) found = aToolbar._getElementByPID(defSetCute[j]); if (found && found.nextSibling) { let check = true; while (check && found.nextSibling) { switch ((_d[i][2] ? found : found.nextSibling).localName) { case "toolbaritem": case "toolbarbutton": check = false; break; default: found = found.nextSibling; } } } beforeElt = found ? (found.nextSibling ? found.nextSibling : null) : (aToolbar.firstChild ? aToolbar.firstChild : null); } for each (var newItemId in _d[i][0].split(",").reverse()) if (!gDocument.getElementById(newItemId)) beforeElt = aToolbar.insertItem(newItemId, beforeElt); } } } // quotes if (aNmb < "4.3.0") { aToolbar.insertItem("separator", null); aToolbar.insertItem("yasearch.cb-default-0", null); aToolbar.insertItem("yasearch.cb-default-1", null); } this._persistToolbarSet(aToolbar); }, module: { registerSelf: function (compMgr, fileSpec, location, type) { var compReg = compMgr.QueryInterface( Ci.nsIComponentRegistrar ); compReg.registerFactoryLocation(this.cid, "nsIYaSearch JS component", this.contractId, fileSpec, location, type); var catman = Cc["@mozilla.org/categorymanager;1"].getService(Ci.nsICategoryManager); catman.addCategoryEntry("app-startup", "nsIYaSearch", this.contractId, true, true); }, unregisterSelf: function(compMgr, fileSpec, location) { compMgr = compMgr.QueryInterface( Ci.nsIComponentRegistrar ); compMgr.unregisterFactoryLocation( this.cid, fileSpec ); var catman = Cc["@mozilla.org/categorymanager;1"].getService(Ci.nsICategoryManager); catman.deleteCategoryEntry("app-startup", this.contractId, true); }, getClassObject: function (compMgr, cid, iid) { if (!cid.equals(this.cid)) throw Cr.NS_ERROR_NO_INTERFACE; if (!iid.equals(Ci.nsIFactory)) throw Cr.NS_ERROR_NOT_IMPLEMENTED; return this.factory; }, cid: Components.ID("{3F79261A-508E-47a3-B61C-D1F29E2068F3}"), contractId: "@yandex.ru/yasearch;1", factory: { createInstance: function (outer, iid) { if (outer != null) throw Cr.NS_ERROR_NO_AGGREGATION; return gYaSearchService; } }, canUnload: function(compMgr) {return true;} } } function NSGetModule(compMgr, fileSpec) { return nsIYaSearch.prototype.module; } var gYaSearchService = new nsIYaSearch();