Je veux utiliser RxJS dans mon socket.on('sense',function(data){});
. Je suis coincé et confus avec très peu de documentation disponible et mon manque de compréhension de RxJS. Voici mon problème.
J'ai un distSensor.js
qui a une fonction pingEnd ()
function pingEnd(x){
socket.emit("sense", dist); //pingEnd is fired when an Interrupt is generated.
}
Dans mon App.js j'ai
io.on('connection', function (socket) {
socket.on('sense', function (data) {
//console.log('sense from App4 was called ' + data);
});
});
La fonction de détection récupère de nombreuses données de capteur que je souhaite filtrer à l'aide de RxJS et je ne sais pas comment procéder pour utiliser les RxJ ici. Tout pointeur vers la documentation ou un échantillon correct serait utile.
Je pense que vous pouvez utiliser Rx.Observable.fromEvent
( https://github.com/Reactive-Extensions/RxJS/blob/master/doc/api/core/operators/fromevent.md ).
Voici comment j'ai fait une chose similaire en utilisant Bacon.js, qui a une API très similaire: https://github.com/raimohanska/bacon-minsk-2015/blob/gh-pages/server.js#L13
Donc dans Bacon.js ça irait comme
io.on('connection', function(socket){
Bacon.fromEvent(socket, "sense")
.filter(function(data) { return true })
.forEach(function(data) { dealWith(data) })
})
Et dans RxJs, vous devriez remplacer Bacon.fromEvent
par Rx.Observable.fromEvent
.
J'ai rencontré des problèmes étranges avec la méthode fromEvent. Je préfère donc créer mon propre observable:
function RxfromIO (io, eventName) {
return Rx.Observable.create(observer => {
io.on(eventName, (data) => {
observer.onNext(data)
});
return {
dispose : io.close
}
});
Je peux alors utiliser comme ceci:
let $connection = RxfromIO(io, 'connection');
Vous pouvez créer un observable comme ceci:
var senses = Rx.Observable.fromEventPattern(
function add (h) {
socket.on('sense',h);
}
);
Utilisez ensuite senses
comme n’importe quel autre observable.
ES6 un liner que j'utilise, en utilisant ES7 bind syntax:
(lire $
comme stream
)
import { Observable } from 'rxjs'
// create socket
const message$ = Observable.create($ => socket.on('message', ::$.next))
// translates to: Observable.create($ => socket.on('message', $.next.bind(this)))
// filter example
const subscription = message$
.filter(message => message.text !== 'spam')
//or .filter(({ text }) => text !== 'spam')
.subscribe(::console.log)
Utilisez simplement fromEvent()
. Voici un exemple complet dans Node.js mais fonctionne de la même manière dans le navigateur. Notez que j’utilise first()
et takeUntil()
pour éviter une fuite de mémoire: first()
n’écoute qu’un événement, puis se termine. Maintenant, utilisez takeUntil()
sur tous les autres événements de socket que vous écoutez afin que les observables se terminent lors de la déconnexion:
const app = require('express')();
const server = require('http').createServer(app);
const io = require('socket.io')(server);
const Rx = require('rxjs/Rx');
connection$ = Rx.Observable.fromEvent(io, 'connection');
connection$.subscribe(socket => {
console.log(`Client connected`);
// Observables
const disconnect$ = Rx.Observable.fromEvent(socket, 'disconnect').first();
const message$ = Rx.Observable.fromEvent(socket, 'message').takeUntil(disconnect$);
// Subscriptions
message$.subscribe(data => {
console.log(`Got message from client with data: ${data}`);
io.emit('message', data); // Emit to all clients
});
disconnect$.subscribe(() => {
console.log(`Client disconnected`);
})
});
server.listen(3000);
Vous pouvez utiliser rxjs-dom,
Rx.DOM.fromWebSocket(url, protocol, [openObserver], [closeObserver])
// an observer for when the socket is open
var openObserver = Rx.Observer.create(function(e) {
console.info('socket open');
// Now it is safe to send a message
socket.onNext('test');
});
// an observer for when the socket is about to close
var closingObserver = Rx.Observer.create(function() {
console.log('socket is about to close');
});
// create a web socket subject
socket = Rx.DOM.fromWebSocket(
'ws://echo.websocket.org',
null, // no protocol
openObserver,
closingObserver);
// subscribing creates the underlying socket and will emit a stream of incoming
// message events
socket.subscribe(
function(e) {
console.log('message: %s', e.data);
},
function(e) {
// errors and "unclean" closes land here
console.error('error: %s', e);
},
function() {
// the socket has been closed
console.info('socket closed');
}
);