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

@@ -89,6 +89,8 @@
import { backInOut } from "svelte/easing";
import { scale } from "svelte/transition";
import { z } from "zod";
import { currentUser } from "$lib/stores/user_store.js";
import Editor from "$lib/components/base/editor.svelte";
let { data } = $props();
@@ -119,7 +121,9 @@
expand: z
.object({
gpx_data: z.string().optional(),
summit_logs: z.array(SummitLogCreateSchema).optional(),
summit_logs_via_trail: z
.array(SummitLogCreateSchema)
.optional(),
waypoints: z
.array(
WaypointCreateSchema.extend({
@@ -469,20 +473,26 @@
}
function beforeSummitLogModalOpen() {
summitLog.set(new SummitLog(new Date().toISOString().split("T")[0]));
const newSummitLog = new SummitLog(
new Date().toISOString().split("T")[0],
);
newSummitLog.author = $currentUser?.actor;
summitLog.set(newSummitLog);
summitLogModal.openModal();
}
function saveSummitLog(log: SummitLog) {
let editedSummitLogIndex = $formData.expand!.summit_logs?.findIndex(
(s) => s.id == log.id,
);
let editedSummitLogIndex =
$formData.expand!.summit_logs_via_trail?.findIndex(
(s) => s.id == log.id,
);
if ((editedSummitLogIndex ?? -1) >= 0) {
$formData.expand!.summit_logs![editedSummitLogIndex!] = log;
$formData.expand!.summit_logs_via_trail![editedSummitLogIndex!] =
log;
} else {
log.id = cryptoRandomString({ length: 15 });
$formData.expand!.summit_logs = [
...($formData.expand!.summit_logs ?? []),
$formData.expand!.summit_logs_via_trail = [
...($formData.expand!.summit_logs_via_trail ?? []),
log,
];
}
@@ -497,9 +507,9 @@
summitLog.set(currentSummitLog);
summitLogModal.openModal();
} else if (item.value === "delete") {
$formData.expand!.summit_logs?.splice(index, 1);
$formData.summit_logs.splice(index, 1);
$formData.expand!.summit_logs = $formData.expand!.summit_logs;
$formData.expand!.summit_logs_via_trail?.splice(index, 1);
$formData.expand!.summit_logs_via_trail =
$formData.expand!.summit_logs_via_trail;
}
}
@@ -604,7 +614,7 @@
);
insertIntoRoute(routeWaypoints);
updateTrailWithRouteData();
normalizeRouteTime()
normalizeRouteTime();
} catch (e) {
console.error(e);
show_toast({
@@ -768,7 +778,7 @@
if ($formData.expand?.gpx_data) {
updateTrailWithRouteData();
}
normalizeRouteTime()
normalizeRouteTime();
} catch (e) {
console.error(e);
show_toast({
@@ -830,7 +840,7 @@
editRoute(data.segment, previousRouteSegment);
insertIntoRoute(nextRouteSegment, data.segment + 1);
normalizeRouteTime()
normalizeRouteTime();
updateTrailWithRouteData();
} catch (e) {
console.error(e);
@@ -1109,8 +1119,11 @@
error={$errors.location}
></TextField>
<Datepicker label={$_("date")} bind:value={$formData.date}></Datepicker>
<Textarea name="description" label={$_("describe-your-trail")}
></Textarea>
<Editor
extraClasses="min-h-24"
bind:value={$formData.description}
label={$_("describe-your-trail")}
></Editor>
<Combobox
bind:value={getTrailTags, setTrailTags}
onupdate={searchTags}
@@ -1195,11 +1208,13 @@
<hr class="border-separator" />
<h3 class="text-xl font-semibold">{$_("summit-book")}</h3>
<ul>
{#each $formData.expand?.summit_logs ?? [] as log, i}
{#each $formData.expand?.summit_logs_via_trail ?? [] as log, i}
<li>
<SummitLogCard
{log}
mode="edit"
mode={log.author == $currentUser?.actor
? "edit"
: "show"}
onchange={(item) =>
handleSummitLogMenuClick(log, i, item)}
></SummitLogCard>

View File

@@ -1,4 +1,3 @@
import { ExpandType } from "$lib/models/list";
import { Trail } from "$lib/models/trail";
import { categories_index } from "$lib/stores/category_store";
import { lists_index } from "$lib/stores/list_store";
@@ -14,13 +13,13 @@ export const load: Load = async ({ params, fetch }) => {
return error(400, "Bad Request")
}
const categories = await categories_index(fetch)
const lists = await lists_index({ q: "", author: user?.id ?? "" }, 1, -1, fetch, ExpandType.None)
const lists = await lists_index({ q: "", author: user?.id ?? "" }, 1, -1, fetch)
let trail: Trail;
if (params.id === "new") {
trail = new Trail("", { category: categories[0] });
} else {
trail = await trails_show(params.id, true, fetch);
trail = await trails_show(params.id, undefined, true, fetch);
}
return { trail: trail, lists: lists }

View File

@@ -1,8 +1,8 @@
<script lang="ts">
import { page } from "$app/state";
import TrailInfoPanel from "$lib/components/trail/trail_info_panel.svelte";
import { trail } from "$lib/stores/trail_store";
import { _ } from "svelte-i18n";
import { page } from "$app/state";
let { data } = $props();
</script>
@@ -12,6 +12,7 @@
activeTab={parseInt(page.url.searchParams.get("t") ?? "0")}
initTrail={data.trail}
mode="overview"
handle={page.params.handle}
></TrailInfoPanel>
{/if}
<svelte:head>

View File

@@ -4,7 +4,7 @@ import { error, type Load, type NumericRange } from "@sveltejs/kit";
export const load: Load = async ({ params, fetch }) => {
try {
const trail = await trails_show(params.id!, true, fetch)
const trail = await trails_show(params.id!, params.handle, true, fetch)
return { trail }
} catch (e) {