S7
zurückArbeiten mit TYPO3 FlashMessages im FrontEnd
15.05.2019
Thema: TYPO3

Using and configuring FlashMessages in the TYPO3 Frontend

Working with TYPO3 FlashMessages in the FrontEnd

Right now I have a system that requires feedback on actions in the frontend. A lot of records for events are created through the frontend by the users of the site. They are created, edited and activated. The user should get a proper message for each action done.

To keep the dynamic I wanted a solution that would work across several extensions and that notifications will be displayed regardless on to which page the user is directed after an action.

The solution I was looking at are the TYPO3 internal FlashMessages. The system that gives feedback in the backend can be used without problems in the frontend.

The Extbase AbstractController already has a method addFlashMessage(). This is good and well, but has the problem that you cannot define a queue. With the premise to have a single place to print the messages in the frontend templates, having a single queue across extensions, this would be a necessity. 

This means I'll build myself my own FlashMessage function. Here I can build my own messages, titles, types and a single pipe (or queue) as I like.

This looks like this:

$message = GeneralUtility::makeInstance(
    FlashMessage::class,
    $body,
    $title,
    $type,
    true
);
$flashMessageService = $this->objectManager->get(FlashMessageService::class);
$messageQueue = $flashMessageService->getMessageQueueByIdentifier($identifier);
$messageQueue->clear();
$messageQueue->addMessage($message);

When we implement this, this is:

$body = 'Body of the Message';
$title = 'Title of the message';
$type = 'Type of the FlashMessage'; //any type of  \TYPO3\CMS\Core\Messaging\AbstractMessage can be used.

For us $identifier is the most important part, because here we define the queue in which the FlashMessage is queued to.

This $identifier should be used globally across the project for getting a unified output of all messages.

But where does this output come from? And globally at that?

Here I found the fitting ViewHelper:

<f:flashMessages>

This ViewHelper catches all incoming FlashMessages and prints them. In a partial this can look something like this:

<html
        xmlns:f="http://typo3.org/ns/TYPO3/Fluid/ViewHelpers"
        xmlns="http://www.w3.org/1999/xhtml"
        lang="en"
        f:schemaLocation="https://fluidtypo3.org/schemas/fluid-master.xsd"
        data-namespace-typo3-fluid="true"
>
<f:flashMessages as="{flashMessages}" queueIdentifier="myIdentifier">
    <f:for each="{flashMessages}" as="flashMessage">
        <div class="flash-message">
            <p>
                <a href="#" class="icon-cancel">close window</a>
            </p>
            <h3 class="icon-ok">{flashMessage.title}</h3>
            <p>{flashMessage.message}</p>
        </div>

    </f:for>
</f:flashMessages>
</html>

Creating a separate partial is necessary because it can come to caching problems. It can happen, for some reasons, that for some time no notifications are printed, and then for some reason all notification in the queue are printed.

To mitigate this effect, as previously mentioned, I put the rendering of the FlashMessages into a separate partial.

In the Template (and really there, not in the Layout) I needed a fixed position where I print all the notifications. And this, in reality, is handled by the VHS viewhelpers. In detail with:

<v:render.uncache>

Link to v:render.uncache documentation

So I include in the website Template at an always visible spot where I want the notifications simply the following line:

<v:render.uncache partial="FlashMessages/Message" arguments="{_all}"/>

A prerequisite for this is that my partial is found under FlashMessages/Message.html.

The effect is now that any extension activated in this TYPO3 project can now send messages to this queue. Additionally I will get the type of the FlashMessage, enabling me to tailor the output to the different statuses (OK, Error, Warning, Notice and Info) by adding matching classes to the html.

In the current project there are already 20 controllers sending FlashMessages based on the different actions or errors like saving, deleting activating, deactivating, record not found or required record missing.

Even the exception handling out of TYPO3 can be utilized here, but for that I will write a separate blogentry, which you can find here