我最近发布了一个类似的问题,但这不是重复的。 为代码沉重的帖子道歉,但我想提供尽可能多的上下文。我在Angular.js应用程序中定义分析工具“Amplitude”作为服务时遇到了问题。服务应该在整个应用程序中充当单身人士(source),所以我很难获得以下行为。
在我的 app.js 文件中,我在.run函数中调用AmplitudeService.logEvent('EVENT_NAME'),该函数成功将事件记录到Amplitude。 注意: Console.log(AmplitudeService)返回一个包含所有正确函数的对象。
但是,当我在任何其他控制器中调用AmplitudeService.logEvent('EVENT_NAME')时,例如 header.js ,我在Amplitude仪表板中看不到任何数据。 注意: Console.log(AmplitudeService)将 header.js 中的相同对象返回到 app.js
返回的对象非常感谢所有见解!
P.S。官方AmplitudeJS SDK is here。我试图通过这个wrapper来实现它。
AmplitudeService.js (source)
注意:如果检查作者的语法,他会在服务结束时返回一个对象。在我的研究中,我已经读过在定义服务函数(source)时使用“this”关键字,并且您不需要像使用Factory那样返回对象,所以我已经更新了它相应
angular.module('AmplitudeService', [])
.service('AmplitudeService',
['$amplitude', '$rootScope', 'amplitudeApiKey', '$location',
function ($amplitude, $rootScope, amplitudeApiKey, $location) {
this.init = function() {
$amplitude.init(amplitudeApiKey, null);
}
this.identifyUser = function(userId, userProperties) {
$amplitude.setUserId(userId);
$amplitude.setUserProperties(userProperties);
}
this.logEvent = function(eventName, params) {
$amplitude.logEvent(eventName, params);
}
}]);
angular-amplitude.js (source)
这允许在整个应用程序中访问“$ amplitude”
(function(){
var module = angular.module('angular-amplitude', ['ng']);
module.provider('$amplitude', [function $amplitudeProvider() {
this.$get = ['$window', function($window) {
(function(e,t){
var r = e.amplitude || {};
var n = t.createElement("script");
n.type = "text/javascript";
n.async = true;
n.src = "https://d24n15hnbwhuhn.buttfront.net/libs/amplitude-2.2.0-min.gz.js";
var s = t.getElementsByTagName("script")[0];
s.parentNode.insertBefore(n,s);
r._q = [];
function a(e){
r[e] = function(){
r._q.push([e].concat(Array.prototype.slice.call(arguments,0)));
}
}
var i = ["init","logEvent","logRevenue","setUserId","setUserProperties","setOptOut","setVersionName","setDomain","setDeviceId","setGlobalUserProperties"];
for(var o = 0; o < i.length; o++){
a(i[o])
}
e.amplitude = r
}
)(window,document);
return $window.amplitude;
}];
}]);
return module;
}());
App.js
angular.module('app', [
'ngRoute',
'angular-amplitude',
'AmplitudeService',
])
.run(['AmplitudeService', function(AmplitudeService){
console.log(AmplitudeService); // Outputs 'Object {}'
AmplitudeService.init();
*AmplitudeService.logEvent('LAUNCHED_SITE'); // This logs the event*
console.log(AmplitudeService); // Outputs 'Object {}'
}])
Header.js
angular.module('app.common.header', [])
.controller('HeaderCtrl', [ '$rootScope', '$scope', '$location','$route', '$window', 'AmplitudeService', function($rootScope, $scope, $location, $route, $window, AmplitudeService){
$scope.goToSearch = function(term) {
$location.path('/search/' + term);
console.log(AmplitudeService); // Outputs 'Object {}'
*AmplitudeService.logEvent('SEARCHED');* // This does not log the event
};
}]);
更新:我尝试将服务切换到工厂,但没有产生任何新结果。
答案 0 :(得分:0)
找到解决方案并希望这对遇到此问题的任何人都有帮助。我的解决方案是通过在app.js中的.run()函数内调用AmplitudeService.init()来初始化SDK,它在我的窗口中初始化了一个幅度对象。从那里开始,我在每个控制器中都包含$ window作为服务,并调用$ window.amplitude.logEvent('event_name_here');
如果您有任何疑问,请随时联系。感谢。
答案 1 :(得分:0)
我们在一个大型项目上遇到了类似的问题,我们为init Amplitude创建了一个wrapper providing a directive,并提供了一个提供logEvent和sendUserId的服务。