biosustain / potion-node

TypeScript client for Flask-Potion
MIT License
8 stars 5 forks source link

question: how to update item and not the resource #17

Closed matt3o closed 8 years ago

matt3o commented 8 years ago

Hey, I am trying to create a small Todo / Note application and need a little help. At some point I am fetching a list of todos / notes from the server. The user may then edit a note and it will be uploaded to the server again. So far I found no other way to implement this than asking the Server to get me the specific item and then call update on the item (which is also the way your API describes it)

The result is an unnessary GET call as I also got the resource via GET. In my case I do have the modified data but no reference to the item (in the example the 'user'). Any ideas how to call update repeating the GET on the item?

Expressed in code it should look like this (AngularJS):

// first GET to the resource
let todos = Todos.query();
(let magic etc.)
item = todos[x];
(modification of the item by the user)
var data = {_id: item._id, 'title': item.title, 'text': item.text, 'user': item.user};
// The way I would expect to work but which doesn't 
item.update(data);
// instead I would be doing something like this using an unncessary get:
let up = Todos.fetch(item._id)
up.then((up) =>  {
    up.update(data);
}

Thanks a lot for your help. Great project by the way - imo this is the best API project for Flask ;)

rolandjitsu commented 8 years ago

@matt3o I can see you are using the private prop _id, you can use .id instead. Furthermore, the id is a readonly prop, so you are not supposed to actually pass it when doing updates.

I think I understand what you are describing, so the items you get from the query cannot be updated, but instead you need to fetch each item you want to update and then do the update.

I need to check if there is a bug there and I will get back to you.

matt3o commented 8 years ago

Perfect, thanks for the quick reply! Yeah exactely, sorry for the long description. About the id: I added it for the server side to know which item has to be updated. Thanks for digging into the problem, very appreciated!

rolandjitsu commented 8 years ago

@matt3o Ok, so after a bit of investigation, what you describe might just be some API confusion. If you take a look at item.spec.ts#L466, you will notice that the items you get back from the query are actually instances of the item you did the query on.

But from your code it looks like you are trying to do the update synchronously. It should look like:

const query = Todos.query();
query.then((todos) => {
    const first = todos[0];
    first.update({done: true}); // `.update()` also returns a promise
});

Alternatively, if you provide support for async/await, then the syntax would look much cleaner:

async function updateTodo() {
    const todos = await Todos.query();
    const first = todos[0];
    await first.update({done: true});
}

And if your backend supports it, it can be even more simple to update a todo:

async function updateTodo(id) {
    const first = await Todos.first({where: {id}});
    await first.update({done: true});
}

I will close this, but feel free to ask any other questions.

matt3o commented 8 years ago

Thanks for the update. I actually never programmed Typescript before and tried to get the code to work with Javascript like syntax. Probably have to look a little into that before trying again. I will try it with your code snippet hoping that it works. Is there a way to use this library in Javascript? I wanted to try jspm and therefore the typescript part but am not completely convinced so far :D

rolandjitsu commented 8 years ago

@matt3o What I wrote above is actually just ES6 (still JavaScript). You do not actually need TypeScript, and the jspm installation uses ES6.

This library is compiled to JavaScript (ES6) when published on NPM, so whenever you install it (via NPM or JSPM) you get a javascript package. Additionally you also get TypeScript type definitions in case you use TypeScript.

You just need to setup some CommonJS env to be able to load it though, either by using JSPM or SystemJS or some other module loader.

I guess you need to look a bit into that and try to understand how the ecosystem works.

matt3o commented 8 years ago

Oh okay, then I missunderstood the first sentence of the documentation

A TypeScript client for APIs written in Flask-Potion.

I now switched from Typescript to Babel and it works. After checking your code I am not really sure what made the difference as it seems you did the same thing I did. Not complaining - it works now, nevertheless it's weird. The example code is great though you could think about making a "real" example repo with working jspm / npm configuration which would certainly be a better start for guys like me. Thanks for your efforts!