Dynamic return status from restler - restler

If I put an #status 201 in my function comments then that's what gets returned always on success. Is there a way to make that dynamic?
For example, I have a putChild($child_id, $team_id) method defined. If the child is not already on the team, then I insert them and return a 201. If they are already on the team though, I just don't do anything. In that case I'd want a 200 status to go back, not a 201.
Not sure how to handle this situation.

With the latest version in the v3 branch, you can do the following in the api method to override the status code at runtime
$this->restler->responseCode = 201;

Related

Podio Item task_count not passed in Filter items

in the ruby as php library I see the task_count being referenced as an attribute however when doing the API call (only tested in ruby) I always get task_count = null.
Can this be fixed? Or another way to quickly get the task count for a larger amount of items?
There is a call to get tasks.
https://developers.podio.com/doc/tasks/get-task-count-38316458
Its returning perfect count for me. I have done the same with Java SDK.It take ref type and id as a parameter.
In your case reftype = Item and id = item id.
Let me know if it helps or you need more details.

Should we always validate resource id in url and body in HTTP PUT request?

Suppose I am updating a employee record
url - /api/employees/10
body -
{
id : 10,
name : xyz
}
Should I validate for the employee id in url is same as in response? Because one employee can hit the url himself but update the data of another employee by sending another value in the PUT body.
If you have to validate, it's likely that you want to use POST. A POST is not idempotent and you are supposed to manage the change.
PUT is idempotent, and it just creates a resource. It implies that you don't actually care what id 10 is and whether it is a new id or an existing id. You just replace id 10 with the resource you supply. You only use PUT when you know what the uri should be.
Yes, if the representation of the object in the body contains its own key, you should validate that it matches the key from the URL. It's an error for the client to try to PUT an object at /api/employees/10 that isn't a valid value for employee #10's record, so you should check for that and report it as an error just as you would check that the object has correct syntax.
I believe that the best error code to return in this case is 422 Unprocessable Entity, but I might be wrong about that.
Another thing you can do instead is don't include the key at all in the body. However I find that keeping the key in makes sense for consistency with the way the same type of object is represented in other parts of the API (possibly embedded inside other objects). This is especially true when using XML (although it looks like you are using JSON here).

Proper resource names of a REST API

Let's say we are making an invoice API. What is a more appropriate resource?
GET
paid_invoices
due_invoices
all_invoices
or
GET
invoices/all
invoices/due
invoices/paid
Additional question: If your API allows marking invoices as paid what's the proper resource?
PUT //where 3 is the id
invoices/3
or
PUT
pay_invoice/3
I would say:
GET /invoices returns all invoices;
A filter can return either paid or due invoices: GET /invoices?state=paid where state can be paid or due.
To mark an invoice as paid, you can either set the corresponding state to your resource, and then you just have to update (replace actually) it using PUT /invoices/<id>.
Alternatively, you can patch your resource: PATCH /invoices/<id>. This method requires a diff like state=paid for example.
It's just a matter of what you want to send to your API (a complete resource, or just the change to apply).
A non-REST solution could be to perform a PATCH request to /invoices/<id>/paid. It's not pure REST but it's ok.

Django queryset with "isnull" argument returning duplicates

I want to only return items that don't have associated images. My relationship is something like this:
class Post(models.Model):
....fields
class Photo(models.Model):
post=models.ForeignKey(Post,blank=True,null=True)
photo=models.FileField(upload_to="pics")
def __unicode__(self):
return str(self.post)
I put together the following query to return Post instances where Photo is not null:
posts=Post.objects.filter(photo__photo__isnull=False)
The problem is that it's returning multiple copies of each Post instance per the number of Photo instances that are related to the Post instance. In other words, one post has 5 photos and it is therefore returning five copies in the queryset. I've looked through the documentation and this is a bit tricky. I ended up using distinct(), but I assume that I can make it work immediately.
Thanks
To return posts that don't have associated photos, use the following query:
posts=Post.objects.filter(photo__isnull=True)
Later in your question you are using isnull=False. As you say, the resulting queryset will return each post once for every photo which is attached to it. To only include each post once in the queryset, use distinct.
posts=Post.objects.filter(photo__isnull=False).distinct()
I'm not sure why you query photo__photo__isnull in you're query -- My answer assumes you should use photo__isnull.
I'm not sure what you mean by "but I assume that I can make it work immediately", but using either distinct(), or order_by() should be the solution to your problem.

WCF Data Service - update a record instead of inserting it

I'm developing a WCF Data Service with self tracking entities and I want to prevent clients from inserting duplicated content. Whenever they POST data without providing a value for the data key, I have to execute some logic to determine whether that data is already present inside my database or not. I've written a Change interceptor like this:
[ChangeInterceptor("MyEntity")]
public void OnChangeEntity(MyEntity item, UpdateOperations operations){
if (operations == UpdateOperations.Add)
{
// Here I search the database to see if a matching record exists.
// If a record is found, I'd like to use its ID and basically change an insertion
// into an update.
item.EntityID = existingEntityID;
item.MarkAsModified();
}
}
However, this is not working. The existingEntityID is ignored and, as a result, the record is always inserted, never updated. Is it even possible to do? Thanks in advance.
Hooray! I managed to do it.
item.EntityID = existingEntityID;
this.CurrentDataSource.ObjectStateManager.ChangeObjectState(item, EntityState.Modified);
I had to change the object state elsewhere, ie. by calling .ChangeObjectState of the ObjectStateManager, which is a property of the underlying EntityContext. I was mislead by the .MarkAsModified() method which, at this point, I'm not sure what it does.