-
-
Notifications
You must be signed in to change notification settings - Fork 4.2k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add Query-String Support to the Router #1773
Comments
Ok now we have two of these :) #1487 Maybe should close older one. |
It seems to me this also has some important implications for the view and the controller. ControllersIt would be nice if the query string could be accessed in the controller or at least in App.ShopRoute = Ember.Route.extend({
model: function(params) {
this.controllerFor('shop').set('currentPage', params.page);
return App.Item.find({
"page": params.page || 1
});
}
}); This means I am stuffing what should be query parameters into dynamic segments. My URLs look like this: App.ShopRoute = Ember.Route.extend({
model: function(params) {
return App.Item.find({
"page": params.page || 1
});
},
setupController: function(controller, model, params) {
this._super;
return controller.set('currentPage', params.page);
}
}); Really, it would be nice if it all just worked out of the box just like collections and individual records:
ViewsThe query string should be able to be set in the view, probably in the linkTo helper: {{ #linkTo 'shop' pageQuery='nextPage' }}Next Page{{ /linkTo }} Assuming Generally interested for feedback on both these ideas. I am not sure if my understanding of ember and javascript are up to the task of tackling these myself, but I would love to contribute any way I can. |
@southpolesteve very useful comments. Currently, all of us use dynamic segments as params. I think we just need to extract query string from URL with router lib and make agreement about providing params to controllers. Maybe we should use separate method on |
+1 to @southpolesteve |
@southpolesteve's comments are valid and provide excellent illustrations. For that reason, I'm closing my issue (#1487). Thanks @caligo-mentis. |
I would like to be able to pass an auth token in the URL to automatically authenticate from an email and be immediately presented with the proper content. E.g. http://www.myapp.com/#/messages/5?auth_token=abc123. From what I can tell (still a newbie) this would be a pain (impossible?) to do with dynamic segments. |
@seanrucker currently you can define the route with dynamic segments like that: this.resource('message', { path: '/messages/:id/:token' }); and use |
Right but I would need to add that to every single route since I could potentially link a user to any page of the site from the email. Is there any way to do that globally? |
Hmm, you can inherit all token-routes from custom abstract route which would just append token to params in |
I'm getting around the issue by using the URL in the form of http://www.myapp.com/?auth_token=abc123/#/messages/5 and parsing the query string manually from window.location. Can you see any issues with this workaround? |
I think the use case of global query params is important - the auth token use case is one scenario, however I'm dealing with global filters that can apply to lots of routes, e.g:
Essentially an ideal implementation will have flexibility when defining which routes accept and handle which query params. |
Also implicit in my previous comment is that nested and array query params should be supported if possible, as in rails style |
I too have a need for query parameter support. Right now I have several pages that need filtering. To circumvent this limitation I store a With this pattern working pretty well, I really wish I could just bind to the |
This comment is out of date, please see https://github.com/alexspeller/ember-query |
@southpolesteve @tylr @caligo-mentis @wycats any thoughts on this implementation? |
This comment is out of date, please see https://github.com/alexspeller/ember-query |
Gist has been update for ember rc1 |
What is missing from the discussion / implementation to get this PR merged (aside from a good suite of tests) ? What else is holding up this issue? |
Essentially everything ;) This isn't even a pull request. Off the top of my head:
I am happy to work on the code issues / tests, however at the moment this is going nowhere without buy in from the ember core team. And as this has a milestone of 1.1 and they all seem quite busy, I doubt this is going to be given serious consideration for a while. If I'm wrong about this, and they'd merge it if it was a proper pull request in javascript, with hash location support and tests, I'd be happy to work on those issues, but I just don't think it's a priority for the team at the moment, and I don't want to waste loads of time doing that right now to then find out that it's not what they want for query string support at all, and that I have a patch that constantly goes out of date against master to maintain until they get around to giving it the consideration it needs. |
By the way, I'm glad that you're using it and it's working for you! |
@toranb there is a new version, |
I've been taking a shot at implementing this in the core, after all Location based solutions (much like the one @alexspeller proposed, I use one for HashLocation), while functional in particular scenarios, are hacks at best..
By the way, all of this is assuming that the query string affects the model at all, which it does for my app (we paginate and sort server side, so query strings params are sent to the API), but I can imagine scenarios in which it influences something on the route/controller, but not the context; in which case you might only want to call .. So that's my two cents. Hopefully I'm not ranting too much :). I'm still positive about implementing this sometime soon, but I'd very much like you guys' opinion on these things. I'll upload my implementation of 1. shortly to clarify what I'm talking about. |
I'm just passing through and haven't given it much thought to the repercussions in implementing this but what about having a syntax similar to Matrix Parameters?
|
Hmm I like that, it's like 3. but the syntax feels less awkward. Won't be any easier to implement though. |
Hmm matrix parameters could work - it may even be the most elegant way to avoid calling deserialize on each route when transitioning - although, with the current solution I have implemented in ember-query, it is possible to affect the model without calling deserialise on every route. As the MyPaginatedRoute = Em.Route.extend({
deserializeParams: function(params, controller) {
controller.set('content', MyModel.find({page: params.page});
}
}); However this is a bit of a hack and I'm sure there are instances where this won't work. Thinking about it, the matrix params approach seems like the best compromise, especially as it allows global state to be maintained in parent routes - in fact, I suspect that matrix params would not even require any changes to ember.js or an extension at all - couldn't you just parse these out with the current route in the parseMatrixParams = function(string) {
params = {};
var pairs = string.split(";");
pairs.forEach(function(pair) {
var kv = pair.split("=");
params[kv[0]]= kv[1];
});
return params;
};
App.Router.map(function() {
this.resource('posts', { path: '/posts/:params' });
});
PostsRoute = Em.Route.extend({
model: function(context) {
params = parseMatrixParams(context.params);
return MyModel.find({page: params.page});
}
}); I haven't tried this and it won't be robust at the moment ("/foos/bar=a-string-with-an-=-sign-and-a-;-in" for example) but is there any reason this won't just work at the moment? |
The main issue with an approach like that is the parameters aren't optional; it forces the URI to end with a slash, although your posts URI should actually just be |
This won't work if you expect the App.Router.map(function() {
this.resource('posts', function() {
this.route('index', { path: ':params' });
});
});
PostsIndexRoute = Ember.Route.extend({
serialize: function() {
// parse and stash params
}
});
PostsRoute = Ember.Route.extend({
model: function() {
return Post.find(stashedParams);
}
}); You'll need latest master to get the PR that fixes this behavior. You'll also need to handle the case when the URL is accessed directly, where |
@kamal could you show where / how you stash these params ? Just curious where these string values get put and pulled from dynamically |
@igorbernstein Too much cake. I can't really think of a compelling use case for this that couldn't be handled by a leafier route looking up information on the parent route that was passed a per-route query string. It shouldn't be ambiguous which route will be using the edit: 🍰 🍰 🍰 |
Hmm also not sure it's desirable. I can probably think of a use case for it, but then you'd have to explain to everyone why there's two types of query strings, which takes preference and when and how they're updated.. We'd spend all day in the kitchen only to see our guests stare in doubt at our cake, which is an octahedron with whipped cream on all sides. |
I've got a decent workaround by create an outer controller that has no view or templates:
It works with the controller context stack and reaching up in the stack to pull arguments from a params controller that sits below the desired controller's route. When you need parameters, you need the params controller, and set a paramsBinding: "controllers.params" A rough example how to do it manually is here: A more involved helper function exists here: Edit: This method doesn't work well, see my below comment for my revised strategy |
@Nthalk thanks for sharing, simple and useful! |
Agreed! @Nthalk could you post a full jsfiddle with a sample app using this? I'm trying to use a model route and found that having "params" be a string that represents multiple model properties a bit awkward so I'm sure I'm just doing it wrong :) |
Okay, after diving into that for a while, I realized my above solution didn't work that well, and there was a different, more usable way of dealing with it: http://jsfiddle.net/fdkPY/7/ The one major caveat of this method is that it crowds the url space. Whereas you once had:
...You cannot use that uri space because it is taken by :params, so you must instead use something like...
...so you don't collide with the resource routes. It's a small price to pay, but you can see from the jsfiddle that this method does indeed work and allows extensions into the show routes:
In my projects lib, I'm planning on adding a WithParams mixin that does the generic parameters lifting. Additionally, there can be an observer that listens to changes on the params and updates the current URI via transitionToRoute, but that's best left to the developer to decide if calling transitionToRoute on an observer is sane. |
This is super required for me to keep state within the url. Example: /session?tool=draw&theme=something&redirect_uri=something Anyone taking a crack at this yet for a pull request? |
@jayphelps have you tried my library? |
@alexspeller I have indeed, but I require history and hash support both (I'm currently using my PR #2685 for AutoLocation). I'd be down adding that support to your library, but if this is indeed something the core team wants in the mainline I'm hoping we can get a PR rolling. |
Ah ok. Well the problem is that my implementation is the most complete, however it's unlikely to be the officially adopted one. I haven't worked on matrix params at all, and am unlikely to in the very near future, although I'd be willing to at some point when I have more time. |
Guys! I've been working on another query parameter workaround lately, and this one I'm pretty excited about. It can be found here: https://github.com/ElteHupkes/ember-query-params . Quick summary: global query string (not my preference, but less impossible to implement), works with linkTo / URL generation, Location independent, minor route configuration. For me personally this is the best solution thusfar - let me know what you think! |
@ElteHupkes great contribution. Do you have an example app which demonstrates it's usage and benefits? |
@cavneb I've cooked something up real quick: http://liveweave.com/QLJ0f1 . Unfortunately these JSFiddle type-things don't show the URL-bar, which really is kind of the point when showing query parameters ^^. You can copy-paste that LiveWeave's code into a HTML-document and it should work though. Any questions, please let me know :)! |
@ElteHupkes it worked great. Here's an example app: https://github.com/cavneb/ember-query-params_example |
@cavneb Nice! I added a link in the README. |
@ElteHupkes I've been a bit busy to update my libary for RC6 at the moment, but it seems our libraries are very similar, in fact when I do update my library I will probably be looking at yours and basing it mainly from your work as it does most of what I need. However I think there are one or two things my library does that yours doesn't (binding params to controller properties is the first one I can think of), and one thing I'm not too keen on with your library (I don't like the In any case, I'd like to ask if you'd be willing to work together on this problem and find a way to combine our efforts? |
@alexspeller Definitely! I'll probably be too busy the upcoming weeks for any serious meddling with the query params (ok part of that will be a vacation, so maybe "unavailable" is a better term ;]), but I think it's a very good idea to put our heads together and start thinking about how we can combine our efforts and make things better for everyone. |
Great! I will start working on some stuff, and I'll file some pull requests to your repo and put a note on my library to look there for RC6 support. Enjoy your holiday, and let's talk when you get back. |
@ElteHupkes @alexspeller God bless both of you for working together to solve this. I wanted to try ember-query but it's not RC6 ready yet.. I already have an app that's near production using ember-query-params, which I really like.. I will integrate your combined efforts as they become available. Thanks again! |
Thanks for taking this on @alexspeller and @ElteHupkes! I just grabbed ElteHupkes/ember-query-params and added it to a project I'm working on to give it a spin and wanted to chime in to agree with one of @alexspeller 's recent comments: I find the |
Hi all, This GH thread is becoming a Tolstoy novel, and I'd like to get some outside thoughts in since I doubt there's all that many people following this thread beyond some of the main contributors. So, if you will, please check out the following Discourse thread and summarize the various approaches you've taken, lessons learned, implementation status, etc., and see if we can't nail the best way to go going forward: http://discuss.emberjs.com/t/query-string-support-in-ember-router/1962 |
I just pushed support for ember master here |
hi alex ember-query doesn't work in IE 9 , I added new issue with error message |
Hi all, there is now a PR for this, please see #3182 |
Closing in favor of discussion on the PR. |
No description provided.
The text was updated successfully, but these errors were encountered: