Open RickEyre opened 5 years ago
I think we would just have to set it here correct?
If this seems like a good idea, I'm happy to make a pull request.
feathers-sync
publishes the service events to all servers. It doesn't really trigger the service call itself. Publishing the events is done by hooking into the service event emitter and replacing it with the synchronization mechanism. So internally all service events are actually handled by feathers-sync
and treated the same and there currently isn't an easy way to know where it came from.
This is why it is recommended to do anything that should only happen once in an after
hook.
Okay I see. This makes it hard to use a reactive model when using Feathers events; which is what I was hoping to adopt.
The utility of feathers events really goes down if I can only use them to update local cache and hook into real-time like the docs suggest.
Is adding this feature something that you're at all interested in? I'm happy to do the work if you are interested and can give some pointers.
If not, I will have to think of how to restructure my application.
Thanks.
How does the reactive model look like?
Definitely not opposed to adding this as a feature but I currently can't think of a good way to make that possible. Basically you'd have to be able to determine what server the event came from and then have that server ignore the corresponding incoming synchronization message. Maybe giving each instance a unique id and passing that along might help.
It's nothing too complicated.
I have a lot of side effects in my application and I like to have those side effects to be owned by the service of the resource that is being mutated by the side effect.
For example, when a person registers with my application I need to subscribe them to notifications. What I would like is for the notification service to handle this through listening for events from the people service, rather than the people service being in charge of subscribing people for notifications.
It just makes the system easier to reason about. The knowledge about how a service works in the system is encapsulated into that service itself and we accomplish this by having the services be in charge of handling their own side effects through listening to events.
Each side effect could potentially cause others which results in the Feather's service events being (kind of) a data stream that is operated on asynchronously.
It works really well and I need to start scaling my application at some point which is where I've run into this issue now.
@daffl thoughts? Anything I can help with here?
So what I think would need to happen is add unique server name to the sync-out
event (in https://github.com/feathersjs-ecosystem/feathers-sync/blob/master/lib/core.js#L47):
return app.emit('sync-out', {
event, path, data, context, name: someServerName
});
And then still emit the event (always call https://github.com/feathersjs-ecosystem/feathers-sync/blob/master/lib/core.js#L38). On sync-in
it would then check if it came from the same server
app.on('sync-in', ({ event, path, data, context, name }) => {
if (name === someServerName) {
return;
}
someServerName
would be set in the configuration. That way it can be backwards compatible, too (it just will use the old behaviour if the name isn't set). Then it is possible to add a flag to the context that differentiates between synchronized and internal calls.
@daffl okay awesome. I can work on a pull request for that then.
Sounds great, let me know if you need anything!
With custom serializer and deserializer support PR #130, can this be achieved by allowing deserialized value to be null?
app.on('sync-in', (rawData) => {
if (rawData === null) return;
// ...
})
I was curious if it's possible / a good idea / already being done, to set the provider value to 'sync' or something when the service call is triggered by feathers sync.
I've read in the docs that it's not advised to use event listeners to modify global state when using feathers-sync, however, if the provider was set this would allow a check to run on the listener before executing.
I'd like to have my listeners modify global state and would also like to use feathers-sync so if this is possible that would be great.