xtablo-source/backend/templates/discussion.templ
2026-05-16 10:32:28 +02:00

93 lines
3.3 KiB
Text

package templates
import (
"time"
"backend/internal/db/sqlc"
"backend/internal/web/ui"
)
templ DiscussionTabFragment(tablo sqlc.Tablo, data DiscussionTabData, form DiscussionForm, errs DiscussionErrors, csrfToken string) {
<div id="discussion-tab" class="space-y-6" data-discussion-stream-url={ DiscussionStreamURL(tablo.ID) }>
<div class="flex flex-wrap items-start justify-between gap-3">
<div>
<h2 class="text-2xl font-semibold leading-tight text-slate-900">Discussion</h2>
<p class="mt-1 text-sm text-slate-600">1 participant</p>
</div>
</div>
<div id="discussion-messages" class="rounded border border-slate-200 bg-white">
if len(data.Messages) == 0 {
@DiscussionEmptyState()
} else {
<div class="divide-y divide-slate-100">
for i, message := range data.Messages {
if DiscussionShowDaySeparator(data.Messages, i) {
@DiscussionDaySeparator(message.CreatedAt)
}
@DiscussionMessageRow(message)
}
</div>
}
</div>
@DiscussionComposer(tablo, form, errs, csrfToken)
</div>
}
templ DiscussionEmptyState() {
<div class="bg-slate-50 px-4 py-8 text-center">
<h3 class="text-xl font-semibold leading-snug text-slate-800">No messages yet</h3>
<p class="mt-2 text-base text-slate-600">Start the discussion for this tablo.</p>
</div>
}
templ DiscussionDaySeparator(createdAt time.Time) {
<div class="bg-slate-50 px-4 py-3 text-center text-sm text-slate-500">
{ DiscussionDateLabel(createdAt) }
</div>
}
templ DiscussionMessageRow(message DiscussionMessageView) {
<article id={ "discussion-message-" + message.ID.String() } data-message-id={ message.ID.String() } class="px-4 py-3">
<div class="flex flex-wrap items-baseline gap-x-2 gap-y-1">
<span class="text-sm font-semibold text-slate-900">{ message.AuthorEmail }</span>
<time class="text-xs text-slate-500" datetime={ message.CreatedAt.Format(time.RFC3339) }>{ DiscussionTimestampLabel(message.CreatedAt) }</time>
</div>
<p class="mt-2 whitespace-pre-wrap break-words text-base leading-6 text-slate-900">{ message.Body }</p>
</article>
}
templ DiscussionComposer(tablo sqlc.Tablo, form DiscussionForm, errs DiscussionErrors, csrfToken string) {
<form
method="POST"
action={ templ.SafeURL(DiscussionPostURL(tablo.ID)) }
hx-post={ DiscussionPostURL(tablo.ID) }
hx-target="#discussion-messages"
hx-swap="beforeend"
hx-on::after-request="if (event.detail.xhr.status >= 200 && event.detail.xhr.status < 300) this.reset()"
class="border-t border-slate-200 pt-4"
>
@ui.CSRFField(csrfToken)
@GeneralError(errs.General)
<div>
<label for="discussion-message-body" class="block text-sm font-medium text-slate-700">Message</label>
<textarea
id="discussion-message-body"
name="body"
rows="4"
maxlength={ DiscussionMaxBodyLengthString() }
placeholder="Write a message..."
class="mt-1 block w-full rounded border border-slate-300 px-3 py-2 text-base leading-6 placeholder-slate-400 focus:border-blue-600 focus:outline-none"
>{ form.Body }</textarea>
@FieldError(errs.Body)
</div>
<div class="mt-3 flex items-center justify-end">
@ui.Button(ui.ButtonProps{
Label: "Send message",
Variant: ui.ButtonVariantDefault,
Tone: ui.ButtonToneSolid,
Size: ui.SizeMD,
Type: "submit",
})
</div>
</form>
}