superseriousbusiness / gotosocial

Fast, fun, small ActivityPub server.
https://docs.gotosocial.org
GNU Affero General Public License v3.0
3.68k stars 311 forks source link

[feature] WASM-based Timeline curation/sorting modules/plugins #1401

Open ShadowJonathan opened 1 year ago

ShadowJonathan commented 1 year ago

Is your feature request related to a problem ?

Extensibility of the timeline, sometimes users just want something different than chronological, and an influx of twitter users instinctively called for an Algorithmic timeline. Personally I don't see this only as a crawling-back of a corporate view on social media, but also the way people personally liked using those timelines, as it gave them content they might like.

I'm not gonna deny that it had consequences, it did, people started gaming it, but a value that non-chronological timelines have is to be able to have more choice in how to follow people. Lists already do this, splitting off a feed into multiples.

However, there's still a problem of people just simply changing their posting behaviours, and so one "smart timeline" I envisioned is one that weights infrequent posters above frequent ones. I.e. a timeline that displays people's feeds in sets of three (their latest posts), but then puts the ones that have posted almost nothing in the last month on the top, to make sure people see infrequent posts over frequent posters.

I'm also not saying that this should be a default, there should be multiple timelines of choice, there's not really "a game" to play if there's multiple systems to game against, all in the same intersection. (Not that I fully expect people on fedi to start gaming the system, but alas)

Describe the solution you'd like.

A way to provide "smart timelines" to people as plugins, modules they can install on their account, or something server admins can install on the server, to then pre-process a timeline, or on demand, from a hermetically sealed box.

The biggest thing this unlocks is a development environment, if the API is standardized, it gives people access to distribute these plugins between servers, try them out, swap them out, and generally personalise their experience. It would probably help them keep up to date, or curate their timeline with intelligence from more than just filters.

I can't say everything that it'll do, but it could free people to do whatever they want for their experience on fedi, without corporate promises or the likes. It's also safe, as WASM is built with sandboxing first, and if we only give it a limited amount of APIs, it cannot do anything else than process a chunk of timeline, and give back the post IDs as it thinks it should be ordered/filtered.

Describe alternatives you've considered.

Lists, and the current chronological timeline. While I think they serve their purpose, I'd like to give people choice and ease-of-choice (and switching) in this case, in a way even someone not-as-tech-literate can navigate.

Additional context.

I originally proposed this in a toot, and someone suggested to make this a WASM module; https://pony.social/@cult/109777488647331234

ShadowJonathan commented 1 year ago

One other thing I want to could mention is wasmtime, and their way to approach long-running WASM modules; https://docs.wasmtime.dev/api/wasmtime/struct.Config.html#method.epoch_interruption

I don't know a corresponding advanced WASM runner in golang, but I'd be surprised if one doesn't exist.

One other thing I want to suggest (and ask) is for every API that'll be used in the initial/experimental phase of the plugin system be marked as such, unstable, so that if more servers start looking at this, we can hopefully waive most promises of stability on that API, keep iterating, standardize the APIs that do persist, and arrive at something everyone can use.

ShadowJonathan commented 1 year ago

Snarky sidenote: I'd love (both sarcastically and unironically) to see someone make an Algorithmic Timeline plugin with this system, observe the cost of running it on small servers, and then backtrack or optimise and polish it, finally teaching this techbase of techbros that compute resources aren't finite, and everything has a cost of running, and they should see it as such.


One additional thing I forgot to mention; It'd be nice if users have a way to "export performance metrics" or "export logs" from their personal accounts (or servers from their server interface, if installed from there) and give them to developers, for development grease.

NyaaaWhatsUpDoc commented 1 year ago

People have been asking for other plugin related things, and mentioning lisp.

I think there's a bigger discussion to be had at some point regarding GTS plugins and deciding on a singular direction to take.

ShadowJonathan commented 1 year ago

If lisp can compile to WASM, or someone wants to ship a runner compiled together with its lisp source, I don't see why this is mutually exclusive. WASM gives much more options than just lisp, though, as almost every compiled language has found a way to target it.

NyaaaWhatsUpDoc commented 1 year ago

Yeah WASM definitely sounds like the better option in that regard. For discussions remaining, there's also coming up with a decent way of abstracting how we do things to increase shared plugin code across different areas of the codebase, a neat way of initializing and managing these runtimes, and just generally not adding technical debt by accepting "it does the job" kind of implementations.

I'm not saying anything about your suggestion with this, it's more just a concern I hold in mind considering the size of this project, which I'm mentioning so you see my thought process -- I'm very apprehensive to let enterprise coding practices enter this codebase. The main culprit being coding to get something done (in enterprise case, by some market deadline) vs. doing it right and not accruing technical debt.

ShadowJonathan commented 1 year ago

Exactly, i'm not thinking about "this needs to be done now", but my suggestion on iteration mainly comes from the fact that "we will not get it right on the first try", we dont know how this'll look like, or how an efficient api will look like, and so we need space to experiment and try things out.

In that regard im mostly inspired by rust, as they poll things from the community and put it in unstable rust, before it is agreed upon that it works well, and then to standardize it. That way, they have the space to experiment and realise that they were wrong. Doing things right the first time is good if you know what the right way is, but I know i dont know the right way, and i don't know anyone else who does, so we should allow ourselves to experiment, and mark those experiments as such, and deprecate never-agreed-to-stabilise APIs when we eventually do.

ShadowJonathan commented 1 year ago

Oh what the hell, wasmtime is available for golang!

https://pkg.go.dev/github.com/bytecodealliance/wasmtime-go#section-readme

So the epoch-based (or fuel-based) interruption I talked about seems to be entirely possible here!

There's also other runtimes, like wasmer (which seems to be touted high) and wazero, but I'm just noting this here as the approach I talked about seems close enough.

The "fuel" strategy in wasmtime could maybe even be used for performance metrics, as well.

ShadowJonathan commented 1 year ago

An additional stray thought; It would become possible for clients to start bundling "server behaviour" with updates and whatnot, to give the server a WASM blob to execute for a custom timeline, and then to receive that timeline in that expected format, to then display to the client in a specific UI.