I would say that Spring HATEOAS doesn't replace DTOs: it builds on top of DTOs. So you can make your DTO class extend ResourceSupport
or wrap it with Resource<T>
.
Since Spring HATEOAS 1.0.0, released in late September 2019, ResourceSupport
and Resource<T>
have been renamed to RepresentationModel
and EntityModel<T>
respectively. Quoting the documentation:
Representation models
The ResourceSupport
/ Resource
/ Resources
/ PagedResources
group of classes never really felt appropriately named. After all, these types do not actually manifest resources but rather representation models that can be enriched with hypermedia information and affordances. Here’s how new names map to the old ones:
ResourceSupport
is now RepresentationModel
Resource
is now EntityModel
Resources
is now CollectionModel
PagedResources
is now PagedModel
What's important, however, is to keep the domain model decoupled from the API model.
The models that represent the domain of your application and the models that represent the data handled by your API are (or at least should be) different concerns. You don’t want to break your API clients when you add, remove or rename a field from the application domain model.
While your service layer operates over the domain/persistence models, your API controllers should operate over a different set of models. As your domain/persistence models evolve to support new business requirements, for example, you may want to create new versions of the API models to support these changes. You also may want to deprecate the old versions of your API as new versions are released. And it’s perfectly possible to achieve when the things are decoupled.
To minimize the boilerplate code of converting the domain model to the API model (and vice versa), you could rely on frameworks such as MapStruct. And you also could consider using Lombok to generate getters, setters, equals()
, hashcode()
and toString()
methods for you.