Open BinaryMuse opened 13 years ago
One (possibly crappy? :) idea for the "change the gem" direction is to check any possible wildcard channels if the signature passed to PrivatePub doesn't match the one for the channel the client is subscribing to in authenticate_subscribe
. For example, if the client is subscribing to /updates/6/chats
, first check to see if the signature is correct for that specific channel (as is done now). If it doesn't, then check the following channels until a match is found (or we run out of channels):
/updates/6/*
/updates/6/**
/updates/*
/updates/**
/*
/**
[Update]
In retrospect, yeah, I think I was right, crappy idea. :) Hopefully the one below isn't quite so crappy.
Another potential solution (that Ryan alluded to in a pull request) would necessitate changes on PrivatePub's JavaScript side, but could be more flexible, namely, making the task of figuring out wildcard channel callbacks the responsibility the PrivatePub
object.
<%= subscribe_to "/updates/#{room.id}/*" %>
<script>
// The following call *actually* subscribes us to /updates/id/* with no server-side changes,
// but PrivatePub calls the correct callback(s) when we receive a message based on the
// channel passed to the "subscribe" method.
PrivatePub.subscribe("/updates/" + id + "/chats", function(data, channel) {
$("#chat").append(data.chat_message);
});
// The following call doesn't subscribe us again (because we're already subscribed
// to /updates/id/*, but adds a new "mapping" in the PrivatePub callback set.
PrivatePub.subscribe("/updates/" + id + "/events", function(data, channel) {
process_event(data);
});
</script>
As mentioned in the afore-linked pull request, this allows us the opportunity to do other neat things, like support wildcards in other parts of the channel (e.g. /updates/*/events
).
[Update]
I assume the best way to handle something like this would be to change
if (callback = PrivatePub.subscription_callbacks[options.channel]) {
callback(message.data, message.channel);
}
to something like
if (callbacks = PrivatePub.find_callbacks_for(options.channel) {
for(var callback in callbacks) {
callback(message.data, message.channel);
}
}
Yep, exactly. This can all be done through the JavaScript without much hassle. However you may want to hold off on any pull requests for now. I will be doing some refactoring of the javascript and adding some tests with Jasmine before adding any additional features.
Excellent. Thanks for your work thus far; this has proven to be very useful!
I'm done refactoring the JavaScript and it now includes Jasmine tests. Feel free to send pull requests around the JavaScript now, but be sure to include tests.
:+1:
When subscribing to channels, Faye allows the channel passed to end in either one or two asterisks to match a wildcard segment or multiple segments recursively. The problem is,
subscribe_to
generates a signature based on the channel being subscribed to. Thus, the JS client cannot subscribe to a wildcard channel unless the exact same string is passed to the helper (and vice versa). For example, harkening back to the classic chat example, the following is not possible:Do you think PrivatePub should be modified to support this, or should the client be responsible for using the
channel
parameter in the callback to figure out what channel the event came from? If the former, how should it be handled?