Bulk Update
This demo shows how to implement a common pattern where rows are selected and then bulk updated. This is accomplished by putting a form around a table, with checkboxes in the table, and then including the checked values in the form submission (POST request)
:
<form
id="checked-contacts"
{ hx.Post("/examples/templ/bulk-update/")... }
{ hx.SwapExtended(
swap.New().Strategy(swap.OuterHTML).Settle(3 * time.Second),
)... }
{ hx.Target("#toast")... }
>
<h3>Select Rows And Activate Or Deactivate Below</h3>
<table>
<thead>
<tr>
<th>Name</th>
<th>Email</th>
<th>Active</th>
</tr>
</thead>
<tbody id="tbody">
for _, user := range users {
<tr>
<td>{ user.Name }</td>
<td>{ user.Email }</td>
<td>
<input
type="checkbox"
name={ user.Email }
if user.Active {
checked
}
/>
</td>
</tr>
}
</tbody>
</table>
<input type="submit" value="Bulk Update"/>
@UpdateToast("")
</form>
The server will bulk-update the statuses based on the values of the checkboxes. We respond with a small toast message about the update to inform the user, and use ARIA to politely announce the update for accessibility.
#toast.htmx-settling {
opacity: 100;
}
#toast {
background: #E1F0DA;
opacity: 0;
transition: opacity 3s ease-out;
}
templ UpdateToast(toast string) {
<span
id="toast"
if toast != "" {
aria-live="polite"
}
>
{ toast }
</span>
}
The cool thing is that, because HTML form inputs already manage their own state, we don’t need to re-render any part of the users table. The active users are already checked and the inactive ones unchecked!
You can see a working example of this code below.