Federation (#327)

* initial commit federation

* more federation

* more federation

* more federation

* completes follow, accept, undo

* add trail create activity

* process trail create activity

* more trail create activity

* adds missing endpoints

* adds update and delete activity

* adds comment activities

* adds activities back

* adds summit logs activities

* deletes follow counts table

* fixes migrations

* fixes migrations

* fixes migrations

* fixes migrations

* adds remote profiles

* ctd

* ctd

* we are getting closer...

* adds public summit logs

* fixes federated trails in lists

* adds remote lists

* adds list activites

* fixes lists

* adds notifications

* adds iri redirect

* fixes comments and summitlogs

* fixes follows and profiles

* adds asynchronous send

* fixes list search

* adds encryption key

* bug fixes

* fixes activity signing

* removes custon activity object types

* adds html editor

* fixes html editor

* fixes display issues on mastodon

* adds federated sharing

* finishes announcements

* fixes small summit log issues

* adds trail likes

* finalizes likes

* fixes images for komoot

* add disable federation option

* adds private profiles

* updates docs

* adds federated comments

* adds trail and comments actvitiypub routes

* adds mentions to editor

* adds mentions to trails, comments, summit logs

* updates theme

* updates theme

* update docs

* update docs

* updates docs

* fixes various frontend problems

* fixes activitypub follows api

* updates docs

* updates docs

---------

Co-authored-by: Christian Beutel <>
This commit is contained in:
Flomp
2025-06-21 10:09:22 +02:00
committed by GitHub
parent 742a6d9d30
commit 9276690d60
356 changed files with 57150 additions and 35470 deletions

View File

@@ -1,3 +1,4 @@
import { browser } from "$app/environment";
import { page } from "$app/state";
import { get } from "svelte/store";
@@ -89,4 +90,62 @@ export function formatTimeSince(date: Date) {
return { unit: "minutes", value: Math.floor(interval) };
}
return { unit: "seconds", value: seconds };
}
export function formatHTMLAsText(html?: string) {
if(!html || !browser) {
return ""
}
// Create a temporary DOM element
const tempDiv = document.createElement("div");
tempDiv.innerHTML = html;
// Replace <br> with newlines to preserve line breaks
tempDiv.querySelectorAll("br").forEach((br) => br.replaceWith("\n"));
// Replace block-level elements with newlines before and after
const blockTags = new Set([
"DIV",
"P",
"LI",
"SECTION",
"ARTICLE",
"HEADER",
"FOOTER",
"ASIDE",
"MAIN",
"NAV",
"FIGURE",
"TABLE",
"TR",
"TD",
"TH",
"UL",
"OL",
"PRE",
]);
tempDiv.querySelectorAll("*").forEach((el) => {
if (blockTags.has(el.tagName)) {
el.insertAdjacentText("beforebegin", "\n");
el.insertAdjacentText("afterend", "\n");
}
});
// Extract the text content
let text = tempDiv.textContent;
if (!text) {
return "";
}
// Replace multiple spaces and newlines with a single one if needed
// Optional: collapse excessive blank lines to max two
text = text
.replace(/[ \t]+\n/g, "\n") // trailing spaces
.replace(/\n[ \t]+/g, "\n") // leading spaces
.replace(/\n{3,}/g, "\n\n") // collapse 3+ newlines
.replace(/[ \t]{2,}/g, " "); // collapse multiple spaces to two
// Trim the result
return text.trim();
}