我正在尝试为AngularJS(1.5.x)实施一个拦截器,它可以测量每个api调用并将每个api调用的持续时间发送到Google Analytics。
我开始使用new Date().getTime()
(function (angular) {
'use strict';
angular.module('MODULE')
.factory('HttpLoadingInterceptor', HttpLoadingInterceptor)
.config(HttpLoadingInterceptorConfig);
HttpLoadingInterceptor.$inject = ['$injector', '$q', 'AnalyticsService', '_'];
HttpLoadingInterceptorConfig.$inject = ['$httpProvider'];
function HttpLoadingInterceptor ($injector, $q, AnalyticsService, _) {
var REQUEST_GA_EVENT_NAME = 'REQUEST';
return {
request: request,
requestError: requestError,
response: response,
responseError: responseError
};
function request (config) {
config.requestTimestamp = now();
return config || $q.when(config);
}
function requestError (rejection) {
rejection.config.responseTimestamp = now();
trackRequest(rejection);
return $q.reject(rejection);
}
function response (response) {
response.config.responseTimestamp = now();
trackRequest(response);
return response || $q.when(response);
}
function responseError (rejection) {
rejection.config.responseTimestamp = now();
trackRequest(rejection);
return $q.reject(rejection);
}
function trackRequest (response) {
if (!_.startsWith(response.config.url, 'api')) {
return;
}
AnalyticsService.trackEvent(
REQUEST_GA_EVENT_NAME,
response.config.url,
response.status,
response.config.responseTimestamp - response.config.requestTimestamp
);
}
function now () {
return new Date().getTime();
}
}
function HttpLoadingInterceptorConfig ($httpProvider) {
$httpProvider.interceptors.push('HttpLoadingInterceptor');
}
})(window.angular);
乍看之下看起来不错,但是比较Chrome中网络标签>中收集的请求的持续时间,我发现在我的代码中收集的请求总是更高(有时很多!)来自Chrome收集的那些。
我想到的另一个想法是使用用户导航API ,因此我将代码更改为:
(function (angular, performance) {
'use strict';
angular.module('MODULE')
.factory('HttpLoadingInterceptor', HttpLoadingInterceptor)
.config(HttpLoadingInterceptorConfig);
HttpLoadingInterceptor.$inject = ['$injector', '$q', 'AnalyticsService', '_'];
HttpLoadingInterceptorConfig.$inject = ['$httpProvider'];
function HttpLoadingInterceptor ($injector, $q, AnalyticsService, _) {
var REQUEST_GA_EVENT_NAME = 'REQUEST';
var measureReqCnt = 1;
return {
request: request,
requestError: requestError,
response: response,
responseError: responseError
};
function request (config) {
if (shouldMeasure(config.url)) {
measureRequest(config);
}
return config || $q.when(config);
}
function requestError (rejection) {
if (shouldMeasure(rejection.config.url)) {
trackRequest(rejection);
}
return $q.reject(rejection);
}
function response (response) {
if (shouldMeasure(response.config.url)) {
trackRequest(response);
}
return response || $q.when(response);
}
function responseError (rejection) {
if (shouldMeasure(rejection.config.url)) {
trackRequest(rejection);
}
return $q.reject(rejection);
}
function shouldMeasure (url) {
return performance && _.startsWith(url, 'api');
}
function measureRequest (config) {
config.measureName = [config.url, measureReqCnt++].join('_');
config.markStartName = [config.measureName, 'start'].join('_');
config.markEndName = [config.measureName, 'end'].join('_');
performance.mark(config.markStartName);
}
function trackRequest (response) {
performance.mark(response.config.markEndName);
performance.measure(response.config.measureName, response.config.markStartName, response.config.markEndName);
var entries = performance.getEntriesByName(response.config.measureName, 'measure');
if (entries && entries.length) {
AnalyticsService.trackEvent(
REQUEST_GA_EVENT_NAME,
response.config.url,
response.status,
entries[0].duration
);
}
}
}
function HttpLoadingInterceptorConfig ($httpProvider) {
$httpProvider.interceptors.push('HttpLoadingInterceptor');
}
})(window.angular, window.performance);
..但我再次收到的结果与 Chrome 收集的结果不同,甚至不是使用new Date().getTime()
我做错了什么?我该怎么做?也许Resource Timing API? AngularJS当然有点强加。
我无法使用用户导航API方法 - window.performacne.getEntries()
来查找我的请求持续时间,因为我无法识别特定请求。每个请求的参数都不可用,我有很多相同的API调用只有不同的参数。
我应该装饰AngularJS使用的原生XHR请求吗?
答案 0 :(得分:0)
如何利用performance.now()? (https://developer.mozilla.org/en-US/docs/Web/API/Performance/now),与仅Date()相比,专为高精度性能跟踪而设计?
请参阅: performance.now() vs Date.now()
另外,你关心绝对数字吗?对于性能跟踪,有时相对是最好的,因为将苹果与橙子进行比较很少会产生真正的数据点。
我的猜测是,在使用什么计时器和时间点之间存在差异。 Chrome Dev工具可能更接近电线"而不是包括应用程序代码。如果它有帮助,我们还有一个API分析和调试工具(www.moesif.com/features),但完全披露我是CEO。