For the function:
- getPhoto(String photoName, int userId, int width)
- PhotoController.java
- http://hostname.com/api/photo/get?photo_name=flower&user_id=123&width=1024
- {protocol}://{domain}/api/{controller_or_service_name}/{short_function_name}?param1=value1¶m2=value2¶mN=valueN
Philosophy
I've worked with dozens of rest API's and also created a few. Some conventions are very simple and easy, some are complex.When creating an API you have three players to think about:
- The developer (probably you)
- The client developer
- The end user
The developer (you)
You are your own client, and so are the developers that will inherit and maintain your code. Creating a self-explanatory API means making it easily expandable.If you are developing a service layer or a controller layer, I suggest adding their name to the path, right after the host:
- host.com/photo/
For the same reason, immediately after, put the short name of the function that handles the parameters:
- host.com/photo/get
- host.com/api/photo/get?photo_name=flower&user_id=123&width=1024
The client developer
If you only had the client on your mind, using query parameters for everything would be the best choice, their order is non-abiding and they are all optional. But this will require creation of a special function for navigating to the right controller and make it imparseable to the user.The end user
If you were only to think about the end user, you would probably use very few query parameters (e.g. id=123) and mostly path sections (e.g. photo/id/123). Path sections are cleaner looking and use one simple delimiter character ("/"), so users have an easier time navigating your API. But this is where user simplicity ends, and developers' complexity begins:- Using a path for dynamic data like a user's id could cause some trouble:
- if the function can handle a null value
- if it includes special characters.
- The order of the parameters is static and the client developer can't just throw them on using a query parameter map.
- Arrays and JSON objects can't fit in a path.
To sum it up:
- http://hostname.com/api/photo/get?photo_name=flower&user_id=123&width=1024
Or in more general terms:
- {protocol}://{domain}/api/{controller_or_service_name}/{short_function_name}?param1=value1¶m2=value2¶mN=valueN
And here are a couple additional examples:
- Function: deAssociateUserAndPhoto(String userId, String photoId)
API: http://hostname.com/api/user/deassociate ?photo=456 user=123 - Function: MapService.getDistance(Point a, Point b)
API: http://hostname.com/api/map/distance?point_a=42.365,31.987&point_b=36.743,28.234