This post was very useful but it still took me a while to understand how to set this up on the server side. Here is the beginner intro to this topic, I am using FastAPI and Python but I’ll try to stay closer to the generic html/http topics.
On the Client
You ship any element to the client with a specific id
. This is an element that you plan to mutate with turbo-streams
, for instance we have this h3
element:
<h3 id="mutandis">Title to be replaced!</h3>
You also ship a button or a submit form. Why? Well we want to click
and get a post
response
from the server.
<form action="/some_server_endpoint" method="post">
<button class="button ">Test Streams</button>
</form>
On the Server
The server should accept post
requests on /some_server_endpoint
url (of course any url will work). Now here is the kick, you want the server to send back response headers like so:
accept: text/vnd.turbo-stream.html
content-length: 137
content-type: text/vnd.turbo-stream.html; charset=utf-8
date: Mon,25 Jan 2021 16:25:25 GMT
server: uvicorn
Two things are critical here:
- That you set the
media_type
totext/vnd.turbo-stream.html
- That you set the header
accept
to be equal totext/vnd.turbo-stream.html
Here below an implementation on the server side in Python and FastAPI
@router.post("/some_server_endpoint", response_class=HTMLResponse)
async def testing(response: Response, frame_name: str = ""):
#Build the html turbo-streams here
return HTMLResponse(
content= #streams html
media_type="text/vnd.turbo-stream.html",
headers={"Accept": "text/vnd.turbo-stream.html"},
)
The html content
of the response should look like this:
<turbo-stream action="replace" id="stream" target="mutandis">
<template>
<h3 id="mutandis">Turbo Stream to the rescue!</h3>
</template>
</turbo-stream>
Note the target
mutandis is the same as the id of the h3
element we want to replace in the dom. Turbo will mutate your dom element on the client like so:
<h3 id="mutandis">Turbo Stream to the rescue!</h3>
Now most important of all, why should we do this?
Replacing multiple dom elements with 1 response
We can have these on the client
<h3 id="mutandis1">Title to be replaced!</h3>
<h3 id="mutandis2">Title to be replaced!</h3>
And with just 1 server response like below we can update both elements:
<turbo-stream action="replace" id="stream" target="mutandis1">
<template>
<h3 id="mutandis1">Turbo Stream!</h3>
</template>
</turbo-stream>
<turbo-stream action="replace" id="stream" target="mutandis2">
<template>
<h3 id="mutandis2">Turbo Stream!</h3>
</template>
</turbo-stream>