angular-actioncable
Version:
Connect Angular to ActionCable
179 lines (137 loc) • 8.78 kB
Markdown
[](https://github.com/angular-actioncable/angular-actioncable/releases)
[](https://travis-ci.org/angular-actioncable/angular-actioncable)
[](http://opensource.org/licenses/MIT)
[](https://coveralls.io/github/angular-actioncable/angular-actioncable?branch=master)
[](https://www.npmjs.com/package/angular-actioncable)
# angular-actioncable
An Angular 1.x service for seamlessly integrating Rails 5 (ActionCable) into frontend Angular code. This service opens and maintains a websocket connection between Angular and ActionCable, reconnecting & resubscribing when the connection has been lost, and desynchronising the clients from one another to ease server-side events like code deploys or server restarts.
<p align="center"><img src="https://cdn.rawgit.com/angular/angular.js/d71dc2f5afec230711351e9f160873a41eb60597/images/logo/AngularJS-Shield.exports/AngularJS-Shield-medium.png" alt="AngularJS"/> <img src="https://rawgit.com/angular-actioncable/angular-actioncable/b6acb7042a39796a7ffa951053145a451d00b8bb/images/gemstone_supported_by_tracks.png" alt="Ruby" /></p>
## Usage
#### How to add this to your project
* Use bower and run `bower install angular-actioncable --save` (preferred)
* Use npm and run `npm install angular-actioncable --save`
* [Download it manually](https://github.com/angular-actioncable/angular-actioncable/blob/1.3.0/dist/angular-actioncable.js)
* CDN for development `https://rawgit.com/angular-actioncable/angular-actioncable/1.3.0/dist/angular-actioncable.js`
* CDN for production `https://cdn.rawgit.com/angular-actioncable/angular-actioncable/1.3.0/dist/angular-actioncable.min.js`
#### The One-Liner. (not recommended, but possible)
```html
<%= action_cable_meta_tag %>
<script src="http://ajax.googleapis.com/ajax/libs/angularjs/1.5.3/angular.min.js"></script>
<script src="bower_components/angular-websocket/dist/angular-websocket.min.js"></script>
<script src="bower_components/angular-actioncable/dist/angular-actioncable.js"></script>
<section ng-controller="SomeController">
<ul>
<li ng-repeat="datum in myData">
{{ datum }}
</li>
</ul>
</section>
<script>
angular.module('YOUR_APP', [
'ngActionCable'
])
.controller('SomeController', function ($scope, ActionCableChannel){
$scope.myData = [];
// connect to ActionCable
(new ActionCableChannel("MyChannel")).subscribe(function(message){ $scope.myData.push(message) });
});
</script>
```
#### A better way
```html
<meta name="action-cable-url" content="ws://localhost:3000/cable"/>
<script src="http://ajax.googleapis.com/ajax/libs/angularjs/1.5.3/angular.min.js"></script>
<script src="bower_components/angular-websocket/dist/angular-websocket.min.js"></script>
<script src="bower_components/angular-actioncable/dist/angular-actioncable.js"></script>
<section ng-controller="SomeController">
<ul>
<li ng-repeat="datum in myData">
{{ datum }}
</li>
</ul>
<input ng-model="inputText" /><button ng-click="sendToMyChannel(inputText)">Send</button>
</section>
<script>
angular.module('YOUR_APP', [
'ngActionCable'
])
.controller('SomeController', function ($scope, ActionCableChannel){
$scope.inputText = "";
$scope.myData = [];
// connect to ActionCable
var consumer = new ActionCableChannel("MyChannel", {user: 42, chat: 37});
var callback = function(message){ $scope.myData.push(message); };
consumer.subscribe(callback).then(function(){
$scope.sendToMyChannel = function(message){ consumer.send(message, 'send_a_message'); };
$scope.$on("$destroy", function(){
consumer.unsubscribe().then(function(){ $scope.sendToMyChannel = undefined; });
});
});
});
</script>
```
```ruby
class MyChannel < ApplicationCable::Channel
# ...
def send_a_message(message)
# ...
end
end
```
## Support
Supports:
- Rails 5.0
## Examples
- [Demo project with Rails 5 backend and Angular frontend](https://github.com/Neil-Ni/rails5-actioncable-angular-demo) from [Neil-Ni](https://github.com/Neil-Ni)
- [Example frontend](https://github.com/CraftAcademy/quizmaster-client/blob/5b026e88e9f29e81a7385b13779f451c7e632f6a/www/js/controllers.js)
## API
### Factory: `ActionCableChannel`
_constructor function_
##### Methods
name | arguments | description
----------------------|----------------------------------------------------------|--------------------------------------------
new | channelName:String<br />channelParams:Hash:_optional_<br />_returns instance_ | Creates and opens an ActionCableChannel instance.<br />`var consumer = new ActionCableChannel('MyChannel', {widget_id: 17});`
subscribe | callback:Function<br />_returns promise_ | Subscribes a callback function to the channel.<br />`consumer.subscribe(function(message){ $scope.thing = message });`
unsubscribe | <br />_returns promise_ | Unsubscribes the callback function from the channel.<br />`consumer.unsubscribe();`
send | message:String<br />action:String:_optional_<br />_returns promise_ | Send a message to an action in Rails. The action is the method name in Ruby.<br />`consumer.send('message');`
onConfirmSubscription | callback:Function | Call each time server registers a subscription.<br />`consumer.onConfirmSubscription(function(){ console.log('subscribed'); });`
### Factory: `ActionCableSocketWrangler`
_singleton_
##### Methods
name | arguments | description
------------|--------------------------------------------------------|--------------------------------------------
start | | Starts ngActionCable services. `ActionCableSocketWrangler.start();`<br />_This will start by default unless disabled._
stop | | Stops ngActionCable services. `ActionCableSocketWrangler.stop();`
##### Properties
_Exactly one will be true at all times._
name | type | description
-----------------|------------------|------------
connected | Property:Boolean | ngActionCable is started and connected live.<br />`ActionCableSocketWrangler.connected;`
connecting | Property:Boolean | ngActionCable is started and trying to establish a connection.<br />`ActionCableSocketWrangler.connecting;`
disconnected | Property:Boolean | ngActionCable is stopped and not connected.<br />`ActionCableSocketWrangler.disconnected;`
### Configuration: `ActionCableConfig`
_value_
##### Properties
_You can override the defaults._
name | type | description
----------|---------|------------
wsUri | String | URI to connect ngActionCable to ActionCable. If this is inside a Rails view, it will be read from the action_cable_meta_tag but can still be overridden.
protocols | Array | Specify protocol headers for the websocket connection. Empty by default.
autoStart | Boolean | Connect automatically? Default is true.<br />`ActionCableConfig.autoStart= false;`
debug | Boolean | Show verbose logs. Default is false.<br />`ActionCableConfig.debug= true;`
```javascript
my_app.run(function (ActionCableConfig){
ActionCableConfig.wsUri= "wss://example.com/cable";
ActionCableConfig.protocols = ['soap', 'wamp'];
ActionCableConfig.autoStart= false;
});
```
## Frequently Asked Questions
* *Q.*: What if the browser doesn't support WebSockets?
* *A.*: This module depends on [angular-websocket](https://github.com/AngularClass/angular-websocket) which will not help; it does not have a fallback story for browsers that do not support WebSockets. Please [check](http://caniuse.com/#feat=websockets) your browser target support.
## Is it any good?
[Yes](http://news.ycombinator.com/item?id=3067434)
## License
[MIT](https://github.com/angular-actioncable/angular-actioncable/blob/master/LICENSE.txt)
#### Development
[Setup development](https://github.com/angular-actioncable/angular-actioncable/blob/master/CONTRIBUTING.md)