Changeset c628db10 in Klonkt


Ignore:
Timestamp:
06/26/2026 09:49:44 AM (2 months ago)
Author:
Robin Genis <roboburr@…>
Branches:
main
Children:
14e2ce1
Parents:
5ceed61
Message:

fix(fediverse): expose cover via Note.image for player-card posts (Cirkel covers)

Hosted-audio posts suppress the image attachment so Mastodon shows the player
card; that left the Cirkel/timeline cards coverless. buildNote now also sets the
Note's AS2 image (Mastodon ignores it), and handleInbox uses it as a cover
fallback. scripts/backfill-cirkel-covers.mjs re-fetches existing coverless
timeline notes to fill them in.

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

Files:
1 added
1 edited

Legend:

Unmodified
Added
Removed
  • src/services/ActivityPubService.js

    r5ceed61 rc628db10  
    241241  };
    242242  if (attachment.length) note.attachment = attachment;
     243  // Playable-audio posts suppress the cover attachment (player card). Still expose
     244  // the cover via AS2 `image` so card/grid consumers (the Klonkt Cirkel) can show
     245  // it — Mastodon ignores a Note's `image`, so the player card is unaffected.
     246  if (post.cover_image_url && playable) {
     247    const cov = abs(post.cover_image_url);
     248    if (cov) note.image = { type: 'Image', mediaType: mediaType(cov), url: cov };
     249  }
    243250  return note;
    244251}
     
    646653        const ai = actorInfo(await resolveActor(actorUri), actorUri);
    647654        const html = HtmlSanitizerService.sanitize(o.content || '');
    648         const media = JSON.stringify((Array.isArray(o.attachment) ? o.attachment : []).map((a) => ({ url: safeUrl(a && a.url), type: (a && a.mediaType) || '' })).filter((m) => m.url));
     655        const _atts = (Array.isArray(o.attachment) ? o.attachment : []).map((a) => ({ url: safeUrl(a && a.url), type: (a && a.mediaType) || '' })).filter((m) => m.url);
     656        // Fallback cover: a Note's `image` (set when the attachment was suppressed
     657        // for a player-card post, e.g. hosted-audio posts).
     658        if (!_atts.some((m) => !m.type || /image/i.test(m.type)) && o.image) {
     659          const _im = Array.isArray(o.image) ? o.image[0] : o.image;
     660          const _iu = safeUrl(typeof _im === 'string' ? _im : (_im && _im.url));
     661          if (_iu) _atts.push({ url: _iu, type: (_im && _im.mediaType) || 'image/jpeg' });
     662        }
     663        const media = JSON.stringify(_atts);
    649664        for (const s of subs) {
    650665          tlStmts().ins.run(o.id, s.slug, actorUri, ai.name, ai.handle, ai.icon, ai.url, html, o.url || null, o.published || null, media);
Note: See TracChangeset for help on using the changeset viewer.