perf-service.mjs (3426B)
1 /* This Source Code Form is subject to the terms of the Mozilla Public 2 * License, v. 2.0. If a copy of the MPL was not distributed with this file, 3 * You can obtain one at http://mozilla.org/MPL/2.0/. */ 4 5 let usablePerfObj = window.performance; 6 7 export function _PerfService(options) { 8 // For testing, so that we can use a fake Window.performance object with 9 // known state. 10 if (options && options.performanceObj) { 11 this._perf = options.performanceObj; 12 } else { 13 this._perf = usablePerfObj; 14 } 15 } 16 17 _PerfService.prototype = { 18 /** 19 * Calls the underlying mark() method on the appropriate Window.performance 20 * object to add a mark with the given name to the appropriate performance 21 * timeline. 22 * 23 * @param {string} name the name to give the current mark 24 * @return {void} 25 */ 26 mark: function mark(str) { 27 this._perf.mark(str); 28 }, 29 30 /** 31 * Calls the underlying getEntriesByName on the appropriate Window.performance 32 * object. 33 * 34 * @param {string} name 35 * @param {string} type eg "mark" 36 * @return {Array} Performance* objects 37 */ 38 getEntriesByName: function getEntriesByName(entryName, type) { 39 return this._perf.getEntriesByName(entryName, type); 40 }, 41 42 /** 43 * The timeOrigin property from the appropriate performance object. 44 * Used to ensure that timestamps from the add-on code and the content code 45 * are comparable. 46 * 47 * Note: If this is called from a context without a window 48 * (eg a JSM in chrome), it will return the timeOrigin of the XUL hidden 49 * window, which appears to be the first created window (and thus 50 * timeOrigin) in the browser. Note also, however, there is also a private 51 * hidden window, presumably for private browsing, which appears to be 52 * created dynamically later. Exactly how/when that shows up needs to be 53 * investigated. 54 * 55 * @return {number} A double of milliseconds with a precision of 0.5us. 56 */ 57 get timeOrigin() { 58 return this._perf.timeOrigin; 59 }, 60 61 /** 62 * Returns the "absolute" version of performance.now(), i.e. one that 63 * should ([bug 1401406](https://bugzilla.mozilla.org/show_bug.cgi?id=1401406) 64 * be comparable across both chrome and content. 65 * 66 * @return {number} 67 */ 68 absNow: function absNow() { 69 return this.timeOrigin + this._perf.now(); 70 }, 71 72 /** 73 * This returns the absolute startTime from the most recent performance.mark() 74 * with the given name. 75 * 76 * @param {string} name the name to lookup the start time for 77 * 78 * @return {number} the returned start time, as a DOMHighResTimeStamp 79 * 80 * @throws {Error} "No Marks with the name ..." if none are available 81 * 82 * Note: Always surround calls to this by try/catch. Otherwise your code 83 * may fail when the `privacy.resistFingerprinting` pref is true. When 84 * this pref is set, all attempts to get marks will likely fail, which will 85 * cause this method to throw. 86 * 87 * See [bug 1369303](https://bugzilla.mozilla.org/show_bug.cgi?id=1369303) 88 * for more info. 89 */ 90 getMostRecentAbsMarkStartByName(entryName) { 91 let entries = this.getEntriesByName(entryName, "mark"); 92 93 if (!entries.length) { 94 throw new Error(`No marks with the name ${entryName}`); 95 } 96 97 let mostRecentEntry = entries[entries.length - 1]; 98 return this._perf.timeOrigin + mostRecentEntry.startTime; 99 }, 100 }; 101 102 export const perfService = new _PerfService();