why paragraph, gone
This commit is contained in:
parent
2defee6b26
commit
ddfbac9dfc
1 changed files with 0 additions and 81 deletions
|
@ -20,87 +20,6 @@ However, it should be understood that this cookbook does _not_ dwell on the
|
||||||
built-in servant combinators as the [Structuring APIs
|
built-in servant combinators as the [Structuring APIs
|
||||||
](<../structuring-apis/StructuringApis.html>) cookbook already covers that angle.
|
](<../structuring-apis/StructuringApis.html>) cookbook already covers that angle.
|
||||||
|
|
||||||
## Why would I want to use `NamedRoutes` over the alternative `:<|>` operator?
|
|
||||||
|
|
||||||
With `NamedRoutes`, we don’t need to care about the declaration order of the endpoints.
|
|
||||||
For example, with the `:<|>` operator there’s room for error when the order of the API type
|
|
||||||
|
|
||||||
```haskell,ignore
|
|
||||||
type API1 = "version" :> Get '[JSON] Version
|
|
||||||
:<|> "movies" :> Get '[JSON] [Movie]
|
|
||||||
```
|
|
||||||
|
|
||||||
does not follow the `Handler` implementation order
|
|
||||||
|
|
||||||
```haskell,ignore
|
|
||||||
apiHandler :: ServerT API1 Handler
|
|
||||||
apiHandler = getMovies
|
|
||||||
:<|> getVersion
|
|
||||||
```
|
|
||||||
|
|
||||||
GHC could scold you with a very tedious message such as :
|
|
||||||
|
|
||||||
```console
|
|
||||||
• Couldn't match type 'Handler NoContent'
|
|
||||||
with 'Movie -> Handler NoContent'
|
|
||||||
Expected type: ServerT MovieCatalogAPI Handler
|
|
||||||
Actual type: Handler Version
|
|
||||||
:<|> ((Maybe SortBy -> Handler [Movie])
|
|
||||||
:<|> ((MovieId -> Handler (Maybe Movie))
|
|
||||||
:<|> ((MovieId -> Movie -> Handler NoContent)
|
|
||||||
:<|> (MovieId -> Handler NoContent))))
|
|
||||||
• In the expression:
|
|
||||||
versionHandler
|
|
||||||
:<|>
|
|
||||||
movieListHandler
|
|
||||||
:<|>
|
|
||||||
getMovieHandler :<|> updateMovieHandler :<|> deleteMovieHandler
|
|
||||||
In an equation for 'server':
|
|
||||||
server
|
|
||||||
= versionHandler
|
|
||||||
:<|>
|
|
||||||
movieListHandler
|
|
||||||
:<|>
|
|
||||||
getMovieHandler :<|> updateMovieHandler :<|> deleteMovieHandler
|
|
||||||
|
|
|
||||||
226 | server = versionHandler
|
|
||||||
```
|
|
||||||
|
|
||||||
On the contrary, with the `NamedRoutes` technique, we refer to the routes by their name:
|
|
||||||
|
|
||||||
```haskell,ignore
|
|
||||||
data API mode = API
|
|
||||||
{ list :: "list" :> ...
|
|
||||||
, delete :: "delete" :> ...
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
and GHC follows the lead :
|
|
||||||
|
|
||||||
```console
|
|
||||||
• Couldn't match type 'NoContent' with 'Movie'
|
|
||||||
Expected type: AsServerT Handler :- Delete '[JSON] Movie
|
|
||||||
Actual type: Handler NoContent
|
|
||||||
• In the 'delete' field of a record
|
|
||||||
In the expression:
|
|
||||||
MovieAPI
|
|
||||||
{get = getMovieHandler movieId,
|
|
||||||
update = updateMovieHandler movieId,
|
|
||||||
delete = deleteMovieHandler movieId}
|
|
||||||
In an equation for 'movieHandler':
|
|
||||||
movieHandler movieId
|
|
||||||
= MovieAPI
|
|
||||||
{get = getMovieHandler movieId,
|
|
||||||
update = updateMovieHandler movieId,
|
|
||||||
delete = deleteMovieHandler movieId}
|
|
||||||
|
|
|
||||||
252 | , delete = deleteMovieHandler movieId
|
|
||||||
```
|
|
||||||
|
|
||||||
So, NamedRoutes is more readable for a human, and GHC gives you more accurate error messages.
|
|
||||||
|
|
||||||
What are we waiting for?
|
|
||||||
|
|
||||||
|
|
||||||
## Boilerplate time!
|
## Boilerplate time!
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue