Changeset 7875a80 in Klonkt for src/views/pages/messages.ejs


Ignore:
Timestamp:
08/06/2026 01:56:08 AM (5 weeks ago)
Author:
Claude (agent) <aiclaude@…>
Branches:
main
Children:
0448e34
Parents:
04aca12
git-author:
Robin <roboburr@…> (08/06/2026 01:55:53 AM)
git-committer:
Claude (agent) <aiclaude@…> (08/06/2026 01:56:08 AM)
Message:

Berichten toont gesprekken: Berichten, Gesprekken en Verzonden vouwen samen

Berichten had zes chips, waarvan drie over hetzelfde gesprek gingen. Een
uitwisseling viel daardoor uit elkaar: wat jij stuurde stond onder Verzonden,
wat je terugkreeg onder Berichten of Gesprekken, en om een draad te volgen moest
je tussen chips heen en weer. Dat waren geen aparte pagina's maar client-side
filters over een enkele lijst, dus het probleem zat in het model, niet in de
weergave.

Antwoorden, mentions en je eigen verzonden berichten vouwen nu samen tot draden.
De sleutel: hangt het bericht aan een post van jou, dan is dat de draad --
ontvangen antwoorden kennen hun post via de join op posts, verzonden antwoorden
via ap_outbox.post_slug, en dat is dezelfde sleutel. Hangt het aan niets van jou
(een mention), dan loopt de draad per tegenpartij. De post wint van de persoon:
twee mensen onder dezelfde post voeren een gesprek, geen twee.

De context hoort bij de draad. Gaat het gesprek over een post, dan staat de link
ernaartoe in de kop, want zonder die context is een los antwoord in een lijst
niet te plaatsen. Binnen de draad leest het van oud naar nieuw, en jouw eigen
bijdragen staan aan de andere kant van de lijn zodat je de beurten ziet zonder
namen te lezen.

Likes, boosts, follows, reports en poll-uitslagen blijven losse regels: dat is
geen gesprek. De chips gaan van zes naar vier: Alles, Gesprekken, Activiteit,
Moderatie.

Twee dingen die daarbij moesten:

  • listOutbox selecteert post_slug (stond in de tabel, werd niet gelezen).
  • De filter kijkt naar ':scope > .msg-item', want de bubbels in een draad zijn geen zelfstandige regels meer; zoeken indexeert een draad op zijn hele tekst in plaats van op de eerste bubbel.

De titel van de post blijft leeg zolang hij onbekend is in plaats van terug te
vallen op de slug: het nieuwste bericht in een draad is vaak je eigen antwoord,
en dat kent alleen de slug -- zou die de titel worden, dan kon het ontvangen
antwoord eronder de echte titel niet meer invullen.

Getest tegen dev.klonkt.com: de groepering en de template gedraaid op de echte
database daar, en op een kopie ervan met een nagebouwd gesprek (twee ontvangen
antwoorden, jouw antwoord ertussen, plus een like). Dat levert een draad van
drie berichten op volgorde met de post als context, terwijl de like een losse
regel blijft. Suite 408/408.

Co-Authored-By: Claude Opus 5 <noreply@…>

File:
1 edited

Legend:

Unmodified
Added
Removed
  • src/views/pages/messages.ejs

    r04aca12 r7875a80  
    2525
    2626  <div class="msg-filters" role="tablist" aria-label="<%= t('msg.title') %>">
     27    <%# Vier chips, geen zes: Berichten, Gesprekken en Verzonden gingen op in
     28        een enkele Gesprekken-view, waarin verzonden en ontvangen in dezelfde
     29        draad staan. Activiteit en Moderatie blijven wat ze waren. %>
    2730    <button type="button" class="msg-chip is-on" data-show="all"><%= t('msg.filter_all') %></button>
    28     <button type="button" class="msg-chip" data-show="msgs"><%= t('msg.filter_msgs') %></button>
    2931    <button type="button" class="msg-chip" data-show="conv"><%= t('msg.filter_conv') %></button>
    3032    <button type="button" class="msg-chip" data-show="act"><%= t('msg.filter_act') %></button>
    3133    <button type="button" class="msg-chip" data-show="mod"><%= t('msg.filter_mod') %></button>
    32     <button type="button" class="msg-chip" data-show="sent"><%= t('msg.filter_sent') %></button>
    3334  </div>
    3435  <div class="msg-search">
     
    7172  var items = [];
    7273  function indexItem(li) {
     74    // Een draad indexeren op zijn eerste bubbel zou de rest onvindbaar maken,
     75    // dus daar nemen we de hele tekst; losse regels blijven gericht geindexeerd.
     76    if (li.classList.contains('msg-thread')) {
     77      li._search = ((li.getAttribute('data-who') || '') + ' ' + li.textContent).toLowerCase();
     78      return;
     79    }
    7380    // Index once: sender + message body + linked post title + poll text.
    7481    var body = li.querySelector('.msg-content');
     
    8289  // items join the filter/search (and inherit the active chip via apply()).
    8390  function reindex() {
    84     items = list ? Array.prototype.slice.call(list.querySelectorAll('.msg-item')) : [];
     91    items = list ? Array.prototype.slice.call(list.querySelectorAll(':scope > .msg-item')) : [];
    8592    items.forEach(function (li) { if (!li._search) indexItem(li); });
    8693  }
     
    138145
    139146  .msg-list { list-style: none; padding: 0; margin: 0; display: flex; flex-direction: column; gap: .55rem; }
     147
     148  /* Een draad is geen regel maar een blok: kop met de context, daaronder de
     149     bubbels van oud naar nieuw. De verticale lijn links maakt zichtbaar dat ze
     150     bij elkaar horen -- dat was precies wat ontbrak toen verzonden en ontvangen
     151     in aparte chips zaten. */
     152  .msg-thread { display: block; }
     153  .msg-thread-head { display: flex; align-items: center; gap: .5rem; flex-wrap: wrap; margin-bottom: .5rem; }
     154  .msg-thread-who { font-weight: 600; }
     155  .msg-thread-count { font-size: .78em; padding: .05rem .4rem; border-radius: 999px;
     156    background: color-mix(in srgb, var(--ink, #000) 10%, transparent); }
     157  .msg-thread-post { display: inline-flex; align-items: center; gap: .3rem; font-size: .85em;
     158    margin-inline-start: auto; max-width: 100%; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
     159  .msg-thread-post svg { width: 13px; height: 13px; flex: none; }
     160  .msg-thread-msgs { list-style: none; margin: 0; padding: 0 0 0 .85rem; display: flex; flex-direction: column; gap: .45rem;
     161    border-inline-start: 2px solid color-mix(in srgb, var(--ink, #000) 10%, transparent); }
     162  .msg-sub { display: flex; gap: .8rem; align-items: flex-start; }
     163  /* Jouw eigen bijdrage staat aan de andere kant van de lijn, zodat je de
     164     beurten ziet zonder namen te lezen. */
     165  .msg-sub.msg-sent { flex-direction: row-reverse; text-align: end; }
     166  .msg-sub.msg-sent .msg-line { justify-content: flex-end; }
    140167
    141168  .msg-item { display: flex; gap: .8rem; padding: .85rem .95rem; border-radius: 14px; align-items: flex-start;
Note: See TracChangeset for help on using the changeset viewer.