Karl Taylor
Karl Taylor

Reputation: 5279

REST API When to use query params or request params?

I have a database with a table that contains workout-plans. An example of the data is here:

{
  id: 1,
  level: 'beginner'
  week_index: 1
},
{
  id: 2,
  level: 'beginner'
  week_index: 2
},
{
  id: 3,
  level: 'advanced'
  week_index: 1
}

What is the best way to get a specific item by using week_index and level. These are my current ideas but I do not know the best practice for a REST API.

/workout-plans?level=beginner&week=1
/workout-plans/beginner/1
/workout-plans/beginner?week=1

Upvotes: 2

Views: 89

Answers (4)

Robert Bräutigam
Robert Bräutigam

Reputation: 7744

The RESTful way to get a specific item would be to create a form. You know, like a form on the web. In this "search form" the client would input the week and level, and would get a result or a redirect to a list of applicable workouts.

The exact URI of the result page is irrelevant, though your first solution with path parameters is compatible with plain HTML forms, so that would work out of the box with HTML GET form, which is good.

In general, always think about what HTML pages you would create for humans, it's usually the ones you should create for REST clients too.

Unless you just want plain JSON over HTTP, in which case there are no such constraints.

Upvotes: 1

RemcoGerlich
RemcoGerlich

Reputation: 31270

/workout-plans/ is the path for the list of workout plans. So it always returns a list, even if there's only 1 result.

So /workout-plans/?level=beginner&week=1 yields 1 result, but as a list.

If that's the desired way to address a single one of them (by level and week, not by id), then the URL to get one of them would be something like

/workout-plans/1/beginner/
/workout-plans/beginner/1/
/workout-plans/beginner-1/

Or something like that.

I prefer the last one, as it doesn't suggest there a level between the full list and the detail path; if you choose the first, then what to do if someone asks /workout-plans/1/.

Upvotes: 2

mahfuz
mahfuz

Reputation: 3223

Solution 1: I recommend this:

I think, you should use /workout-plans?level=beginner&week=1. Because, in this way it is clear that you are requesting data from workout-plans controller.


Solution 2, another way:

Or, you can use: /workout-plans/level/beginner/week/1

Such as: in Rails, route configuration can be like this:
/workout-plans/level/:level/week/:week


I hope, it helps.

Upvotes: 1

Sombriks
Sombriks

Reputation: 3622

First add significance to each HTTP verb.

  • with GET you can list and find one single result
  • use POST to insert
  • PUT or PATCH for updates
  • use DELETE to get rid of data under a certain key.

Avoid path parameters as filters, prefer query parameters to do that.

It's relatively simple to build a rest client to rely on such contract.

Also, special query parameters such as page and pageSize with proper default values are welcome.

Since you're designing an API, try to return meaningful status codes and messages.

This article has more detailed info and for some other point of view, see this opinionated article, pick the HATEOAS.

Upvotes: -1

Related Questions