I'm doing a rewrite of an old Rails application and I thought I should do it in a RESTful manner, as a learning experience if nothing else.
I've reached some actions that toggles a boolean value, for example if an article is published or not.
Before I had a couple of actions: toggle_published, publish and unpublish.
They were very easy to use: i just made a link to them in the article-list.
How would you do the same thing in a RESTful manner?
Should I use the update-action, and build a mini-form to replace each l开发者_高级运维ink that I used before? I don't particulary like that idea.
Just a notice:
A toggle method is not RESTful, because the HTTP PUT verb is supposed to be idempotent (see a.o. http://en.wikipedia.org/wiki/Idempotence#Examples). This means that no matter how often you execute a method, it should always give the same result. A toggle method does not adhere to this principle, as it does not give the same result if you execute it once comparing to executing it twice.
If you want to make it RESTful, you should create two methods: one for setting and one for unsetting.
Making an application RESTful does not only mean that you should use the correct HTTP verb.
I'd probably solve it with PUT/DELETE or POST/DELETE on a nested "toggle resource". Perhaps not 100% completely restful but certainly easy enough to understand.
PUT or POST /articles/:id/published # Toggle published ON
DELETE /articles/:id/published # Toggle published OFF
GET /articles/:id/published # Get state RESTfully via status 200 (ON) or 404 (OFF)
Might seem a bit odd, but it is technically RESTful.
Update: A (perhaps) more natural approach might also just be:
PUT or POST /articles/:id/published Data: { state: true/false } # Toggle published ON
You could also use the PATCH
verb with the actual article which I assume has a published
property:
PATCH /articles/:id { published: true/false }
Because all the cool REST kids are using PATCH nowadays.
It sounds like you have two use cases:
- set published state
- toggle published state
You should be able to add a member route for the toggle action for:
/articles/<id>/toggle_published - calls Article.toggle(:published)
And use Article update on :published attribute via the standard REST resource route.
map.resources :articles, :member => :toggle
I like @Van der Hoorn answer
so in real life we are using in login & logout scenario
use post or put or patch
/users/login -> with some payload data
/users/logout
In Above Eg login & logout is almost acting like setting boolean Flag , Easy to read and set in db
Eg : so its no harm to use same idea in toggle context
use post or put or patch
/book/3/publish
/book/4/unpublish
Note . :
1 : use this approach if there is only 1 field to be toggled , else if there are multiple fields then general /book/4
a patch request with payload data will do
2 : use this approach if there is any security layer is implemented so it will be like
Eg :
Editor -> can access urls like `/books/:id` & `/books/:id/publish`
Senior Editor -> can access urls like `/books/:id` & `/books/:id/unpublish`
精彩评论