Building entity views
How entity views work
An EntityView
is created by an EntityViewFactory
based on an EntityViewRequest
.
A controller is still responsible for executing (usually rendering) the actual EntityView
.
The GenericEntityViewController
is responsible for loading and rendering all default views in the AdminWebModule UI.
The path of the web request to GenericEntityViewController
will determine:
-
the name of the view that should be rendered
-
which
EntityViewRegistry
will be used for loading the view (EntityConfiguration
orEntityAssociation
)
You can force the view being rendered by simply providing the view name as a request parameter with key view. |
The controller creates an EntityViewRequest
, retrieves the EntityViewFactory
and builds the corresponding EntityViewContext
and EntityViewCommand
.
EntityViewRequest
Wraps together all the information of a specific entity view request:
-
the web request that is creating the view
-
the contextual information of the entity being viewed (represented by the
EntityViewContext
) -
the command that should be executed on the
EntityViewFactory
(represented by theEntityViewCommand
) -
the name of the view being requested and the
EntityViewFactory
being used -
the
PageContentStructure
of the page being rendered (if applicable)
Please refer to the EntityViewRequest
javadoc for a description of all available properties.
EntityViewContext
The EntityViewContext
contains contextual information and provides access to components that should be used for building a view.
Contextual information is for example the entity type, specific entity or entity association being viewed.
Components are things like the EntityLinkBuilder
, EntityMessages
or AllowableActions
Please refer to the EntityViewContext
javadoc for a description of all available properties.
EntityViewContext is available as a request-scoped bean but only in case of a request passing through the GenericEntityViewController will the data be loaded.
Loading the EntityViewContext attributes manually can be done by using the EntityViewContextLoader bean.
You should use the ConfigurableEntityViewContext interface to modify a view context.
|
EntityViewCommand
The EntityViewCommand
represents the command that should be executed on the EntityViewFactory
to create the corresponding EntityView
.
Most often the command represents the form of a view where the request parameters are bound to.
An EntityViewCommand
has 2 attributes: the (optional) entity DTO being bound and a map of named extensions.
Customizing view processing can be done by registering additional extensions that will be rendered and validated upon binding.
The EntityViewCommand
will be validated for every state modifying request: web requests using POST, PUT, PATCH or DELETE.
Please refer to the EntityViewCommand
javadoc for a description of all available properties.
EntityViewFactory
Every view is built by an EntityViewFactory
.
An EntityViewRegistry
(like EntityConfiguration
or EntiyAssociation
) is nothing but a map of EntityViewFactory
by view name.
An EntityViewFactory
is a stateless controller with 4 controller methods that are expected to be called in a specific order.
Please refer to the javadoc for an overview of the different controller methods and their purpose.
DispatchingEntityViewFactory
EntityModule has only a single implementation of EntityViewFactory
in the form of the DefaultEntityViewFactory
.
The DefaultEntityViewFactory
:
-
supports
ViewElement
based rendering model - heavily used by EntityModule for building the HTML markup -
dispatches its controller methods in a more fine-grained manner to a list of registered and ordered
EntityViewProcessor
instances.
The default builders when configuring views only register EntityViewProcessor
beans on the factory.
When an EntityViewFactory
controller method is being called, it will be translated into one or more processor methods and those method calls will be dispatched to all processors in order.
The DefaultEntityViewFactory will not execute any of the rendering related methods if any of the previous methods has marked the EntityView as being a redirect or have specified their own ResponseEntity .
|
EntityViewProcessor
EntityViewProcessor
classes allow to hook into the execution of a view request.
View processors give access to the configuration of the context for the request and the actual execution of the request.
This enables us to perform most, if not all, of the logic executed during a request by using view processors.
Configuring the context
- Initialization of the
EntityViewContext
-
prepareEntityViewContext
allows for modifications to theEntityViewContext
which holds information about the entity configuration or entity that is viewed. - Authorization of the request
-
An
authorizeRequest
method is provided that should throw a relevant exception if the request is invalid. - Initialization of the
EntityViewCommand
-
Initializes the
EntityViewCommand
for the current request. TheEntityViewCommand
represents the command object to handle the form data. It will hold the DTO for the entity that is being created or updated and supports the configuration of additional extension objects that should be bound and validated as well.initializeCommandObject
allows you configure theEntityViewCommand
for use in the remainder of the request lifecycle.
Executing a request
The execution of the view request has two aspects, executing the request and rendering elements. A request is handled in various lifecycle steps.
- Preprocessing
-
Actions that should be taken before the request is handled, such as validating the command object. This is done in the
preProcess
step of an EntityViewProcessor. - Executing the request
-
The actual execution of the request, performed via the
doControl
step. In this step, the controller logic is executed, such as saving an entity and building a response. - Rendering
-
An optional step. If rendering should be applied, three additional methods are used to build the elements that should be rendered on the view.
-
preRender
: This is the point where theViewElementBuilderContext
is configured andViewElementBuilders
are created. -
render
: Where the initial rendering happens. At this point, most of the configuration has been executed and the elements that should be rendered are finalized. -
postRender
: Perform render related postprocessing. This step is commonly used to modify the view after all the elements have been created, such as moving items within the layout.
Various utility methods are available through the
ContainerViewElementUtils
, for manipulating container view elements, andEntityViewElementUtils
for working with view elements and view building. -
- Postprocessing
-
General purpose postprocessing of the request when the view has been fully processed and is ready to be returned to the user.
postProcess
is the final step in the execution of a view and is always executed.
For ease of use, several specialized adapter classes have been provided to hook into the rendering process:
-
EntityViewProcessorAdapter
for most use cases, it provides several adapter methods that also allow you to hook into theViewElement
generation lifecycle -
SimpleEntityViewProcessorAdapter
if you do not need to hook into theViewElement
generation lifecycle -
ExtensionViewProcessorAdapter
if you want to create a custom view/form that represents a so-called extension object-
the view is part of the entity configuration but often does not manage properties of the actual entity type
-
Please refer to the appendix for a list of all available general purpose processors.
Transaction support
The DefaultEntityViewFactory
uses a TransactionalEntityViewProcessorRegistry
and enables transactions on all state modifying HTTP methods: POST, PUT, PATCH or DELETE.
If a transaction manager bean name is available on the EntityConfiguration
, transactions will be enabled by default for all form views: create, update, delete and custom form views.
This means that all calls in state modifying doControl()
methods of all EntityViewProcessor
instances will happen in a single transaction.
The transaction manager bean name is registered as an attribute EntityAttributes.TRANSACTION_MANAGER_NAME
and is detected automatically for every Spring Data repository based entity.
You can enable transactions manually on the EntityViewFactoryBuilder
by specifying either the PlatformTransactionManager
to use, the name of the transaction manager bean or a TransactionTemplate
if you need more fine-grained control.
Model attributes
The GenericEntityViewController
exposes the following model attributes to the Spring MVC view:
Attribute name | Value |
---|---|
entityViewRequest |
|
entityViewCommand |
|
entityViewContext |
|
Default view types
EntityModule supports 3 view types by default.
When defining a new view (see the next section) it will be one of these types.
The view type determines the base template that will be used to setup the EntityViewFactory
.
The following view types are defined:
View type | Template name | Description |
---|---|---|
list view |
listView
( |
Base configuration for rendering a list of entities. |
form view |
updateView
( |
Base configuration for rendering a form for a single entity. |
generic view |
genericView
( |
Barebone configuration for visualizing a single entity. |
The template name can be used to replace the initializer for the EntityViewFactoryBuilder
.
See the chapter on the EntityViewFactoryBuilderInitializer.
See also the next chapters for more information on list view, form view and generic view.