In this video, explore how to add navigation properties to collection pages to improve discoverability in the API.
- [Instructor] If we want our paged collection responses to truly satisfy the HATEOAS constraint, they should include navigation properties that allow the client to move through the pages by following links on the pages. The PagedCollection class already includes these navigation properties. The next step is to write some code that will automatically populate these links. I'll make a new static method at the top of this class called, public static PagedCollection of T, Create, and this'll take a self link, an array of items, an int size for the total size of the collection, and an instance of PagingOptions.
And all this method is gonna do is create a new PagedCollection of T, and copy over these items, to say Self equals self, Value equals items, Size equals size, Offset comes from the pagingOptions dot Offset, Limit comes from the pagingOptions dot Limit, the First link is just self, and then for the next, previous, and last links, we need to write some new methods.
We'll say Next equals GetNextLink, given self, size, and pagingOptions. Previous will be very similar. We'll call this GetPreviousLink, and Last equals GetLastLink. All right, we need to write these three methods. I'll do this at the bottom so I don't clutter up the class too much. This'll be a private method.
This'll return a link and it'll be called GetNextLink, and of course it takes itself, and an int size and a pagingOptions. We need to do a little bit of logic in here. If the pagingOptions instance dot Limit is null for some reason, we'll just return null. And same for the Offset.
If those aren't null, we need to do some math. Let's do limit, pagingOptions dot Limit dot Value, since we'll be referring to it a bunch, and we'll do the same for the offset. Let's calculate the value of the next page, so we'll say, nextPage equals the offset plus the limit, and if that's bigger than the total size, we'll just return null.
If not, we need to build up the parameters that will be used in the URL of the next request. We'll say var parameters, parameters, equals new RouteValueDictionary, which is a class from ASP.NET Core dot routing. We'll include these original RouteValues from the self link, and then we'll modify the limit to be limit, and the offset to be nextPage.
And then we'll generate a new link, newLink equals Link dot ToCollection given self dot RouteName, and then all of these new parameters, return that newLink. The methods for the previous and last links are similar. They both include some math to calculate the proper offset values. I'm gonna paste these in from the exercise files. Now we can go over to the Rooms controller and in GetAllRoomOpenings, now we'll change this var collection line.
It's no longer going to create a new PagedCollection, it's going to do PagedCollection of Opening dot Create and we need to pass these values here, Link dot, this will come from here, Link dot ToCollection. The items is openings dot Items dot ToArray, then we have size, which is openings dot totalSize, and the paging options we'll just pass right through, so pagingOptions.
Now clients will have a smooth, nice experience while navigating through these paged results. Let's give it a try over in Postman. If I hit the openings route with no parameters, I'll get the default offset of zero and the limit of 25. This collection actually has 27 items in it, so I can see what that next link looks like. The next link is generated with limit 25, offset 25, which should grab me the last two items in the collection.
And there we go, we've got the last two. I can always go previous or just go to the beginning, which is slash rooms, slash openings with no parameters. That wraps up our look at adding pagination to the API. You should feel comfortable adding paging options to your own hypermedia collections. If you want an additional challenge, add paging to the GetAllRooms method, and then add a navigation link between GetAllRooms and GetAllRoomOpenings. If you want to see my solution, open up the beginning exercise files for the next video.
- What is RESTful design?
- Building a new API with ASP.NET Core
- Using HTTP methods
- Returning JSON
- Creating RESTful routing with templates
- Securing RESTful APIs with HTTPS
- Representing resources
- Representing links
- Representing collections
- Sorting and searching collections
- Building forms
- Adding caching to an ASP.NET Core API
- Configuring user authentication and authorization