Issues with DS.Store#createRecord


#1

Hello guys,

I’m currently stuck with a problem with ember-data. When persisting a model using the code in an ArrayController:

...
var card = this.store.createRecord('card', {
  name: name,
  number: number
});
card.save(onSuccess, onFailure)
...

My problem begins when the server returns a validation error (invalid number format for example, status code 4xx). The createRecord always create the element in the interface, I can even comment the save function and it still presents my invalid element. I don’t want it, I want to wait for my server to respond before showing the new element.

I can’t figure out how I can do it in since the createRecord don’t make any http call, and I need to use it to create my record. This is silly.

What can I do?

Thanks in advance.


#2

When you call .save() and the save is successful it changes the isNew property to false. In your case, the save is not successful so that property is never flipped to false. There is also an isError property that is set on records that were unsuccessful. All you need to do is filter your results on the UI to on display items !isNew or on isError.

Here is an example I whipped up of how you can achieve this.


#3

You should do your validation in your view IMHO. The save() is simply for persisting the store.

I like to think of the use of createRecord to mean that the record is a real model of something. So, for instance, if you have a real cat named Ginger, and you have a cats database, you want to call createRecord to get an instance of Cat that is Ginger. Ginger is valid and real, and happens to not be saved in the persistence layer yet… saving her to the persistence layer should not be about whether you want her to exist or not, it should be about persisting her representation. That’s it.

Put another way, your form shouldn’t have a model in it. Your form should have data attributes that are then instantiated into a model when the user hits “create”… the controller responsible for creating that model (ie using createRecord) shouldn’t actually create the record if it’s not valid.

Does that make sense?


#4

Thanks guys,

Jasonmit, your solutions is pretty decent and solved my problem.

Julian, I don’t know if I got your point. But imagine our cat persistence layer don’t accept persians cats, and Ginger is persian. The traditional solution to this problem is:

POST /cats {name: 'Ginger', type: 'Persian'}

RESPONSE 4XX 
{ errors: 'Your cat is persian, get out!' }

Yes, I can do the validation also on the client side, but I think this violates so badly the DRY principle and I try to avoid this unless it’s strictly necessary.

Another solution is to make one HTTP call just to validade the cat and call createRecord only after that, but I don’t like it as well.

Fortunately, the isNew solve my problem. But I’m still concerned about the createRecord philosophy. I’m loving Ember though.


#5

Fair enough. Probably why Ember Data isn’t ready for primetime yet. Should probably mention this in the Ember Data project. :wink: It’s a use case that we see often.

That’s an interesting use case, though. I’ve got a similar one in my app, too. I have some fairly complicated rendering logic duplicated between my backend and my front end. They’re in different languages. The front end has to do live rendering of it, and the back has to do the final rendering.

It very much feels like it’s violating DRY, except that I’d have to build some form of advanced language-agnostic meta-pattern or language to place that logic in only one place. Wasn’t really sure how to tackle that. Also, the front side and back side logic is subtlely different because of different language features and the fact that one of them is built in an Async front side, whereas the other is built in a more Sync language.

Fascinating! :slight_smile:

What would probably be really cool is if we had some form of validation API we could communicate against in Ember-Data… something like the Active Record pattern by Martin Fowler… whereby there are two APIs - one for the schema, and one for the data. :wink: That schema could also specify validation information which could inform ember of how to validate on various data.

Going on from there, it’d be quite cool if we had our server partially building out the JS that makes up the Ember application to provide common algorithms across server and client in only one place… using some kind of meta-language.

But I digress, and this is sounding like “Intentional Programming” :wink: now…