-
-
Save vanchelo/052f0929580f9c353572fa99d6ede02b to your computer and use it in GitHub Desktop.
AngularJS namespaced socket.io service concept
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
'use strict'; | |
/** | |
* Пример использования socket.io namespaces в сервисе AngularJS. | |
* | |
* Цель: получить несколько отдельных каналов связи в рамках одного соединения. | |
* | |
* Проблема: так как сервисы в AngularJS являются синглтонами, не возможно | |
* получить несколько экземпляров сервиса Socket с разными значениями | |
* namespace. При этом хочется иметь отдельные сервисы, представляющие | |
* каналы связи в socket.io. | |
* Решение: делаем сервис Socket конструктором, а отдельные каналы связи - именованными | |
* сервисами-экземплярами сервиса Socket (или его наследниками). | |
* | |
* @inspired by http://www.html5rocks.com/en/tutorials/frameworks/angular-websockets/ | |
*/ | |
var services = angular.module('myApp.services', []); | |
// Concept: | |
services.factory('Socket', ['$rootScope', function($rootScope) { | |
var connections = {}; | |
function getConnection(channel) { | |
if (!connections[channel]) { | |
connections[channel] = io.connect('http://localhost:3000/' + channel); | |
} | |
return connections[channel]; | |
} | |
function Socket(namespace) { | |
this.namespace = namespace; | |
} | |
Socket.prototype.on = function(eventName, callback) { | |
var con = getConnection(this.namespace), self = this; | |
con.on(eventName, function() { | |
var args = arguments; | |
$rootScope.$apply(function() { | |
callback.apply(con, args); | |
}); | |
}); | |
}; | |
Socket.prototype.emit = function(eventName, data, callback) { | |
var con = getConnection(this.namespace); | |
con.emit(eventName, data, function() { | |
var args = arguments; | |
$rootScope.$apply(function() { | |
if (callback) { | |
callback.apply(con, args); | |
} | |
}); | |
}) | |
}; | |
return Socket; | |
}]); | |
// Examples: | |
services.factory('channelFoo', ['Socket', function(Socket) { | |
return new Socket('foo'); | |
}]); | |
services.factory('channelBar', ['Socket', function(Socket) { | |
function ChannelBar() { | |
this.namespace = 'bar'; | |
} | |
ChannelBar.prototype = angular.extend(Socket.prototype, {}); | |
ChannelBar.prototype.start = function() { | |
this.emit('start'); | |
}; | |
ChannelBar.prototype.exit = function() { | |
this.emit('exit'); | |
}; | |
return new ChannelBar(); | |
}]); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment