How do I display a route parameter? - ember.js

I'm trying to understand Ember. I can't quite work it out. I currently have the routes:
/participants
/list
/search/:query
And I'm trying to figure out how to get my search page to display that query parameter. The navigation works, I just can't figure out how to display that "query" bit (ie, "You searched for Bennie")
(One thing I tried is that I have an App.ParticipantsSearchController with a 'searchtext' in it, and I know I can display that with {{searchtext}} in the template, but even if I try to later do an App.ParticipantsSearchController.searchtext = 'abc', that doesn't get updated. So that doesn't seem to do me any good.)
I would really appreciate the help from somebody who understands Ember better than I do.

Part of the problem is the parameter is supposed to be representing a unique id of a model representing that resource. If you are going in and randomly changing the unique id, technically your model should be completely different. If your model is completely different you should be transitioning to the route using transitionTo from the route(or transitionToRoute from controller) to switch out models.
And intuitivepixel is correct, you need to be using the set on your model, model.set('searchtext', 'mooooooo');
What will really help you will be the query params that Alex Speller is implementing for Ember. See http://discuss.emberjs.com/t/query-string-support-in-ember-router/1962/44. Until then you'll be doing some really weird transitioning in order to get the url to represent the model. Maybe the url shouldn't update until they've pressed search, or something along those lines. And then in that case, you could call transitionTo/transitionToRoute and then the url would be able to match the current model, so you could type in the url and get straight to that search result. BTW, you can add multiple slugs to a single resource if you are going to have multiple search things. If you do that you'll need to add the serialize method to specify each property...
/search/:age/:sex/:country
serialize: function(model) {
// this will make the URL `/search/12/M/Brazil`
return { age: model.age, sex: model.sex, country: model.country };
}

Related

Ember: get target url from afterModel

I have two paths pointing to the same route:
this.route('items', { path: ':fruitName/rotten' });
this.route('items', { path: ':fruitName' });
I am trying to get the current URL from within the afterModel hook of the /items/fruitName route. If I use this.get('router.url'), it will give me the previous URL before the transition. I need to detect if the target has 'rotten' at the end of the path.
I found that transition.intent.url has the path as a string, but only when its manually entered into the browser. If I click a link to transtion, transition.intent.url is undefined.
How can I determine if the transition URL is /items/fruitName/ or /items/FruitName/rotten?
Before determine which url you have, my question is : how do you make a transition with a different url to the same route (by using {{link-to}}) ?
In your case, you have the same route for 2 different purpose, I understand what you want to accomplish but you will break ember rules (which force you to make a bad design).
You can accomplish what you want to do by using nested routes. let me explain:
/:fruitName and /:fruitName/rotten have the same base (same data): a page for a fruit but in the rotten route, you want to display in another tab.
It's a design problem not a route problem, you can make the most of nested route to:
use index to display main content
subroute to display other thing
you can check an example here with a basic css tab.
Could you use queryParams for this? So your URL would look something like this:
items/tomato?rotten=false
or perhaps you want to go with something more generic:
items/tomato?state=rotten
The route and controller will be set up something like what can be found here: https://guides.emberjs.com/v2.14.0/routing/query-params/

Ember-Model: How to establish a hasMany or belongsTo relationship by using a "foreign key"?

Summary
I have a bit of a problem using Ember-Model, trying to establish a unique relationship between two models.
Based on current responses that I have received here on S.O., Ember Forums, and #emberjs. I am beginning to believe that there is no built-in solution for this problem, and I am reformatting my question to specify what is needed.
Details
I am populating a template currently with a full set of debtor information. All the information comes from multiple calls to the server.
The first bit is the basic Debtor info. This part is easy because I can use the model hook and a dynamic segment to retrieve it.
My server returns a JSON for a Debtor... Here's the short version:
{
"debtor" = {
"debtor_id": 1003,
"debtor_name": Steve,
//... more JSON
"debtor_contact_id": 1345
}
}
The dynamic segment for Debtor is filled with the value of the debtor_id, but also notice this debtor has a debtor_contact_id. Every Debtor record retrieved from the server has a unique debtor_contact_id. On the database, this value is a "foreign key" that will tell which contact table belongs to which debtor table.
There is no way to predict which contact info relates to which debtor without this key/value pair.
I currently have "Contacts" belongsTo "Debtor", but that is not enough to do the job.
When it is time to fill the "Contacts" model. Ember-Model needs to know to build the value from debtor_contact_id into the ajax URL as a query parameter in order to GET the correct API.
I am still learning all of this stuff and so far I have not been able to fully follow any tutorials because my use case has an extra step needed somewhere.
This is the expected behavior I am hoping to see:
Model hook will work as expected to pull the specific debtor and put it into a "debtor" model (this part is currently working just fine)
Somehow "debtor_contact_id" is read from the payload
that value is added as part of a server query to find a separate API
the resulting contact info will be pulled into a "contact" model
hopefully a hasMany/belongsTo relationship can be established after both corresponding models are returned.
all this needs to be done in one promise before entering my template
You will also find the question at: discuss.emberjs.com if that is more appropriate place to discuss.
I can elaborate more if this does not make sense... thanks!
Assuming you are using ember-data, alongside the attributes of your model you need to add:
debtor_contact: DS.belongsTo('name_of_the_other_model')
This then provides you a promise which will resolve to the other model on demand. It won't resolve straight away, but bound variables in templates will update as it is resolved. The other API call will be made for you if things are set up properly.
http://emberjs.com/api/data/classes/DS.html#method_belongsTo
The answer I gave here might also be helpful if you need to force resolving the relationship for some reason: Ember Unbound & Belongsto

Where to save detailed user session information for EmberJS app?

I am building my first EmberJS app, and am still trying to wrap my head around the best practices & conventions. I'm using ember-data to talk to a RESTful API, and have ember-auth working well enough to log in and save a user's ID & OAuth2 access token. However, I'd now like to maintain additional user information (e.g. name, email, etc) for use in the navbar and in various other areas of the app.
To do this, I am thinking it would be helpful to have a User object (model) that is read from a separate endpoint (e.g. /users/<id>). Since this info would be needed throughout the app, I'm inclined to store it on the ApplicationController, somewhat like this example from Ember's docs:
App.ApplicationController = Ember.Controller.extend({
// the initial value of the `search` property
search: '',
query: function() {
// the current value of the text field
var query = this.get('search');
this.transitionToRoute('search', { query: query });
}
});
However, my user object wouldn't quite be an action like query or a property like search, so I'm not sure this example applies.
I think I'll eventually want to call something like:
this.get('store').find('user', App.Auth.get('userId'));
but I'm just not sure where in the app that would go.
Main question: is the ApplicationController the right place for this information per Ember conventions, and if so, what might the code look like to retrieve it from the REST API?
Appreciate any thoughts to put me on the right track.
The general approach that I've taken before is to store the currently logged in user as App.CurrentUser. Then you can use it in any template. Once I've pulled the User object I call Ember.set('App.CurrentUser',user) to store it, and then Ember.get('App.CurrentUser') to retrieve it in other routes or controllers.
Here's a short jsbin with the general idea : http://jsbin.com/ucanam/994/edit

How do I get the current/previous view name in Ember

I am right a project and I need to be able to access the name of the previous view.
So, for instance, if I'm on page 1 and I navigate to page 2, I want to know that I came from page 1.
Basically I have a view that can be accessed from a number of screens and the content of that view will depend on the screen that if came from.
I know I can do this by passing the name across in a function, but I am wondering if there is a nicer way of doing this.
I tried some implementations with the historylocation class but I could get it working. The url kept being sent back to the base url every time I created an instance of the historylocation, which was weird.
I also see that there might be a way to do this in the router by adding
location: 'history'
but I don't know how to get this to start working afterwards then, to access the correct view name i.e. current/previous
There a way of getting this through the browser history too I guess but I was hoping to do it with Ember.
Any one have any ideas how to get these to work or better ways to do it?

Assigning a "database id" to multiple html ids on a page

I will use model.id when referencing the id for the table in the database, and id when referencing the id given to elements in my html.
I have a django project where I am using some hidden form fields (all forms have the same id right now for that hidden field) to house the model.id. This works great as long as the model.id is known when the page is rendered.
I am now attempting to modify the process to work when no model.id is given (ie someone has chosen to create a new instance of my model). As far as the backend goes I have this working. No model.id supplied and the view knows it should give empty forms. At this point I choose not to create a new instance of the model, as I only want to if the user actually enters something in one of the forms.
If the user enters something in a form then the form processing creates a new instance of model and passes the id back to the users browser. What I was attempting to do is use the jquery form plugin to save the return data somewhere hidden, which I would then look at and use val to set all of the hidden fields' ids to the model.id that was returned so the next field/form the user submits will know to write to the model that was just created.
Now looking at this I'm guessing the idea of having multiple elements with the same id is bad, but I really do want them to always be the same and only have the hidden fields there to house that same Model.id on every form on the page.
I tried doing something like follows. However only one of the ids on the page actually got the value assigned. Is there a different way I should be accomplishing this goal? Is there something I should add to make all occurrences of id to be set with something like .val(model.id)? If not, does anyone have any suggestions on how to go about this? Maybe django provides a cleaner way of doing exactly what I'm trying to accomplish?
A response returned from form submission.
<response>
<the_model_id_brought_back>3732</the_model_id_brought_back>
...
<response>
The jQuery code attempting to set all of the "id_in_multiple_places" ids to the model.id returned.
jQuery('#descriptionForm').ajaxForm({
target: '#response',
success: function(data) {
the_model_id = jQuery('#response').find("the_model_id_brought_back").html();
jQuery('#id_in_multiple_places').val(the_model_id);
}
});
To explain why I have multiple forms like this. Forms consist of 1 visible field. Multiple forms are on the page. When a user leaves a field (which means they leave the form as well) I will submit that form to the server. This will allow their data to always be saved even if they stop half way through and throw their computer out a window. They can go to a different computer and pick up where they left off.
Thanks.
Now looking at this I'm guessing the idea of having multiple elements with the same id is bad
It's not only bad, it's impossible. You cannot do this. You can get around this by using classes, which don't have to be unique, but you probably shouldn't.
What you should do, is assign the elements sensible class names, and assign their common ancestor the ID. You can start at that element and traverse downwards to find the sub-elements by class name.