UNPKG

@socialwebfoundation/ap-components

Version:

A collection of Web Components for displaying objects from the ActivityPub API

103 lines (93 loc) 2.7 kB
import { html, css, unsafeHTML } from 'https://cdn.jsdelivr.net/gh/lit/dist@3/all/lit-all.min.js'; import DOMPurify from 'https://cdn.jsdelivr.net/npm/dompurify@3.2.3/+esm'; import { ActivityPubElement } from './ap-element.js'; export class ActivityPubNote extends ActivityPubElement { static get properties() { return { ...super.properties, _attributedTo: { type: Object, state: true }, } } static styles = [super.styles, css` :host { display: block; min-width: var(--ap-min-width); min-height: var(--ap-min-height); } .icon { float: left; margin-right: 8px; } .skeleton { min-width: var(--ap-min-width); min-height: var(--ap-min-height); background-color: lightgray; } `]; constructor() { super(); } render() { if (this._error) { return html` <div class="note"> <p class="error">${this._error}</p> </div> ` } else if (!this.json) { return html` <div class="note"> <div class="skeleton"></div> </div> ` } else if (!this._attributedTo) { return html` <div class="note"> <div class="skeleton"></div> </div> ` } else { return html` <div class="note"> <avatar-icon class="icon" size="64" url="${this.getIcon(this._attributedTo)}"></avatar-icon> <p class="name">${this._attributedTo.name}</p> <div class="content"> ${unsafeHTML(DOMPurify.sanitize(this.content))} </div> <p class="published"> <a class="url" href="${this.url}"> ${this.published} </a> </p> </div> `; } } updated(changedProperties) { super.updated(changedProperties); if (changedProperties.has('json')) { this.fetchAttributedTo(); } } async fetchAttributedTo() { if (this.json?.attributedTo) { if (typeof this.json.attributedTo === 'object') { this._attributedTo = this.json.attributedTo; } else if (typeof this.json.attributedTo === 'string') { try { const fn = this.constructor.fetchFunction; const headers = { Accept: this.constructor.MEDIA_TYPES.join(', ') }; const response = await fn(this.json.attributedTo, { headers }); if (!response.ok) { throw new Error(`HTTP ${response.status} ${response.statusText}`); } const json = await response.json(); this._attributedTo = json; } catch (error) { this._error = error.message; } } } } } customElements.define('ap-note', ActivityPubNote);