diff --git a/src/Analytics.js b/src/Analytics.js index 5f4a0d0c77..ab47d30c1d 100644 --- a/src/Analytics.js +++ b/src/Analytics.js @@ -74,6 +74,7 @@ class Analytics { this._paq = null; this.disabled = true; this.firstPage = true; + this.generationTimeMs = null; } /** @@ -147,6 +148,23 @@ class Analytics { return true; } + startPageChangeTimer() { + performance.clearMarks('riot_page_change_start'); + performance.mark('riot_page_change_start'); + } + + stopPageChangeTimer() { + performance.mark('riot_page_change_stop'); + performance.measure( + 'riot_page_change_delta', + 'riot_page_change_start', + 'riot_page_change_stop', + ); + + const measurement = performance.getEntriesByName('riot_page_change_delta').pop(); + this.generationTimeMs = measurement.duration; + } + trackPageChange() { if (this.disabled) return; if (this.firstPage) { @@ -156,6 +174,9 @@ class Analytics { return; } this._paq.push(['setCustomUrl', getRedactedUrl()]); + if (typeof this.generationTimeMs === 'number') { + this._paq.push(['setGenerationTimeMs', this.generationTimeMs]); + } this._paq.push(['trackPageView']); } diff --git a/src/components/structures/MatrixChat.js b/src/components/structures/MatrixChat.js index 1312abda09..a898808141 100644 --- a/src/components/structures/MatrixChat.js +++ b/src/components/structures/MatrixChat.js @@ -368,13 +368,29 @@ export default React.createClass({ window.removeEventListener('resize', this.handleResize); }, - componentDidUpdate: function() { + componentWillUpdate: function(props, state) { + if (this.shouldTrackPageChange(this.state, state)) { + Analytics.startPageChangeTimer(); + } + }, + + componentDidUpdate: function(prevProps, prevState) { + if (this.shouldTrackPageChange(prevState, this.state)) { + Analytics.stopPageChangeTimer(); + Analytics.trackPageChange(); + } if (this.focusComposer) { dis.dispatch({action: 'focus_composer'}); this.focusComposer = false; } }, + shouldTrackPageChange(prevState, state) { + return prevState.currentRoomId !== state.currentRoomId || + prevState.view !== state.view || + prevState.page_type !== state.page_type; + }, + setStateForNewView: function(state) { if (state.view === undefined) { throw new Error("setStateForNewView with no view!"); @@ -1341,7 +1357,6 @@ export default React.createClass({ if (this.props.onNewScreen) { this.props.onNewScreen(screen); } - Analytics.trackPageChange(); }, onAliasClick: function(event, alias) {