Frontend and UI #8

Open
opened 3 weeks ago by Ta180m · 4 comments
Ta180m commented 3 weeks ago
Owner

As I mentioned at the July federation meetup, the UI for federated features is a huge challenge. Currently, I have some Ruby scripts and hand-write ActivityStreams objects, but that's tedious and error-prone. Since designing and implementing the UI will be time-consuming, I think we should start now.

Fortunately, we have a secret weapon: Gitea already has a fully-featured UI for local actions. Since the goal of federation is to use one account across all instances in a seamless way, federated features should overall have a very similar UI as the local version of the feature. For instance, opening a pull request on a remote repo should feel almost the exact same as opening one locally. Of course, there are some situations where the local and federated version of the feature will be different, but overall, we aren't starting from scratch but already have a lot to work with.

So, my idea for implementing the UI is to lazily reuse the existing UI for most features, but add the federation handling into internal functions. For instance, the issues.CreateCommentCtx() internal function is used to create issues and used by the web UI and API. If we add some additional code inside that function for when the target repo is a remote repo (i.e. its owner has @ in their name), then opening an issue on a remote repo will work perfectly without any other changes. (One small detail to worry about is if the remote instance is down, in which case creating the issue should fail).

For rendering remote users, orgs, and repos, I propose again that we can reuse the existing UI, and add a link on those pages to the remote instance, like what Mastodon does:

image

We will also need an /authorize_interaction?uri= endpoint since this is what other AP software use. When this endpoint is given a URL of a AS object, it fetches the object and renders it on your instance. For instance, if Alice has an instance at alice.com and goes to https://alice.com/authorize_interaction?uri=https://bobert.com/api/v1/activitypub/user/bobert, it should fetch Bobert's account's Person object, then redirect Alice to https://alice.com/bobert@bobert.com where Bobert's remote account is rendered as I proposed above. We could even include a text box somewhere where users can paste in the URL of a remote user and then are redirected to the /authorize_interaction?uri= endpoint, similar to how in Mastodon, you can paste a URL into the search bar and Mastodon will render the remote AS object.

The final piece of the puzzle is to display UI buttons like follow, star, fork, etc on Gitea when you are not logged in. The purpose of this is for when you are browsing a user or repo on a remote instance. When you click the UI buttons, a pop-up box should appear that instructs you to type in your instance, and then you are redirected to the /authorize_interaction?uri= endpoint.

There are also some additional federation-specific UIs that we should consider implementing: blocking or reporting users/content and user/organization migrations.

Once we implement all of these components above, Gitea will finally have a usable UI for federated features! 🎉

However, this is probably not the optimal UI. @dachary conducted some user research last year that might be useful for finding ways to improve the UI and UX. Since the local and federated versions of the UI will be similar, it's likely that some problems with the UI will apply to both the local and federated version.

As I mentioned at the [July federation meetup](https://gitea.com/Ta180m/gitea/wiki/July-presentation), the UI for federated features is a huge challenge. Currently, I have some [Ruby scripts](https://gitea.com/Ta180m/aptools) and hand-write ActivityStreams objects, but that's tedious and error-prone. Since designing and implementing the UI will be time-consuming, I think we should start now. Fortunately, we have a secret weapon: Gitea already has a fully-featured UI for local actions. Since the goal of federation is to use one account across all instances in a seamless way, federated features should overall have a very similar UI as the local version of the feature. For instance, opening a pull request on a remote repo should feel almost the exact same as opening one locally. Of course, there are some situations where the local and federated version of the feature will be different, but overall, we aren't starting from scratch but already have a lot to work with. So, my idea for implementing the UI is to lazily reuse the existing UI for most features, but add the federation handling into internal functions. For instance, the `issues.CreateCommentCtx()` internal function is used to create issues and used by the web UI and API. If we add some additional code inside that function for when the target repo is a remote repo (i.e. its owner has `@` in their name), then opening an issue on a remote repo will work perfectly without any other changes. (One small detail to worry about is if the remote instance is down, in which case creating the issue should fail). For rendering remote users, orgs, and repos, I propose again that we can reuse the existing UI, and add a link on those pages to the remote instance, like what Mastodon does: ![image](/attachments/9f5003e8-8c44-4bbc-9906-f056400996a1) We will also need an `/authorize_interaction?uri=` endpoint since this is what other AP software use. When this endpoint is given a URL of a AS object, it fetches the object and renders it on your instance. For instance, if Alice has an instance at alice.com and goes to `https://alice.com/authorize_interaction?uri=https://bobert.com/api/v1/activitypub/user/bobert`, it should fetch Bobert's account's Person object, then redirect Alice to https://alice.com/bobert@bobert.com where Bobert's remote account is rendered as I proposed above. We could even include a text box somewhere where users can paste in the URL of a remote user and then are redirected to the `/authorize_interaction?uri=` endpoint, similar to how in Mastodon, you can paste a URL into the search bar and Mastodon will render the remote AS object. The final piece of the puzzle is to display UI buttons like follow, star, fork, etc on Gitea when you are not logged in. The purpose of this is for when you are browsing a user or repo on a remote instance. When you click the UI buttons, a pop-up box should appear that instructs you to type in your instance, and then you are redirected to the `/authorize_interaction?uri=` endpoint. There are also some additional federation-specific UIs that we should consider implementing: blocking or reporting users/content and user/organization migrations. Once we implement all of these components above, Gitea will finally have a usable UI for federated features! 🎉 However, this is probably not the *optimal* UI. @dachary conducted some [user research](https://lab.forgefriends.org/fedeproxy/ux/-/wikis/home) last year that might be useful for finding ways to improve the UI and UX. Since the local and federated versions of the UI will be similar, it's likely that some problems with the UI will apply to both the local and federated version.

You've clearly been putting a lot of thought into this, which is great to see, and I like your approach.

A few thoughts:

Since the goal of federation is to use one account across all instances in a seamless way, federated features should overall have a very similar UI as the local version of the feature. For instance, opening a pull request on a remote repo should feel almost the exact same as opening one locally. Of course, there are some situations where the local and federated version of the feature will be different, but overall, we aren't starting from scratch but already have a lot to work with.

I agree with this 100%. The less difference between interacting with an repo on a remote instance and interacting with a local one, the better.

We will also need an /authorize_interaction?uri= endpoint since this is what other AP software use.

This is not strictly right; that URI isn't standard and or hard-coded. Each AP software has their own URI. It's advertised over WebFinger as the template property of a link with a rel of http://ostatus.org/schema/1.0/subscribe.

Examples (links are to WebFinger URLs):

  • Mastodon: /authorize_interaction?uri={uri}
  • Bonfire: /pub/remote_interaction?acct={uri}
  • Misskey: /authorize-follow?acct={uri}
  • PeerTube: /remote-interaction?uri={uri}
  • GoToSocial doesn't advertise a template (probably because it doesn't have a web UI)
  • PixelFed doesn't advertise a template
  • Lemmy doesn't seem to use WebFinger

We can pick our own path for this and advertise it via WebFinger.

redirect Alice to https://alice.com/bobert@bobert.com where Bobert's remote account is rendered as I proposed above

This is great for people. What about organisations? Would it be just the same? I guess there's no reason why it shouldn't.

We could even include a text box somewhere where users can paste in the URL of a remote user and then are redirected to the /authorize_interaction?uri= endpoint, similar to how in Mastodon, you can paste a URL into the search bar and Mastodon will render the remote AS object.

I would suggest that rather than a new search box, this should work with the existing search box at /explore/repos.

(I'd also argue that that search box should be visible in the global nav bar, not just at that URL, but that's a generic Gitea UI issue rather than being specific to federation.)

That's all I have for now, but I'll think about this more as I get a chance and come back with any ideas I think of.

You've clearly been putting a lot of thought into this, which is great to see, and I like your approach. A few thoughts: > Since the goal of federation is to use one account across all instances in a seamless way, federated features should overall have a very similar UI as the local version of the feature. For instance, opening a pull request on a remote repo should feel almost the exact same as opening one locally. Of course, there are some situations where the local and federated version of the feature will be different, but overall, we aren't starting from scratch but already have a lot to work with. I agree with this 100%. The less difference between interacting with an repo on a remote instance and interacting with a local one, the better. > We will also need an /authorize_interaction?uri= endpoint since this is what other AP software use. This is not strictly right; that URI isn't standard and or hard-coded. Each AP software has their own URI. It's advertised over WebFinger as the `template` property of a `link` with a `rel` of `http://ostatus.org/schema/1.0/subscribe`. Examples (links are to WebFinger URLs): - [Mastodon](https://indieweb.social/.well-known/webfinger/?resource=acct:caesar@indieweb.social): `/authorize_interaction?uri={uri}` - [Bonfire](https://playground.bonfire.cafe/.well-known/webfinger/?resource=acct:caesar@playground.bonfire.cafe): `/pub/remote_interaction?acct={uri}` - [Misskey](https://misskey.io/.well-known/webfinger?resource=acct:@syuilo@misskey.io): `/authorize-follow?acct={uri}` - [PeerTube](https://tube.network.europa.eu/.well-known/webfinger?resource=acct:edps_podcasts@tube.network.europa.eu): `/remote-interaction?uri={uri}` - [GoToSocial](https://gts.superseriousbusiness.org/.well-known/webfinger?resource=acct:@gotosocial@superseriousbusiness.org) doesn't advertise a `template` (probably because it doesn't have a web UI) - [PixelFed](https://pixelfed.social/.well-known/webfinger/?resource=acct:@dansup@pixelfed.social) doesn't advertise a `template` - [Lemmy](https://lemmy.ml/.well-known/webfinger/?resource=acct:caesar@lemmy.ml) doesn't seem to use WebFinger We can pick our own path for this and advertise it via WebFinger. > redirect Alice to https://alice.com/bobert@bobert.com where Bobert's remote account is rendered as I proposed above This is great for people. What about organisations? Would it be just the same? I guess there's no reason why it shouldn't. > We could even include a text box somewhere where users can paste in the URL of a remote user and then are redirected to the /authorize_interaction?uri= endpoint, similar to how in Mastodon, you can paste a URL into the search bar and Mastodon will render the remote AS object. I would suggest that rather than a new search box, this should work with the [existing search box at `/explore/repos`](https://codeberg.org/explore/repos). (I'd also argue that that search box should be visible in the global nav bar, not just at that URL, but that's a generic Gitea UI issue rather than being specific to federation.) That's all I have for now, but I'll think about this more as I get a chance and come back with any ideas I think of.

There is also the issue (as briefly discussed on Matrix this morning) of how remote repos are represented, as opposed to just remote accounts.

I guess that following on from the idea of https://alice.com/bobert@bobert.com, Alice could see and interact with Bobert's foo repo via something like https://alice.com/bobert@bobert.com/foo.

There is also the issue (as briefly [discussed on Matrix](https://matrix.to/#/!SakSkZqjzMsaPCVqlv:matrix.batsense.net/$KoO3t6HauoV3VU97pIAJJD4GUtZAXNqDajpoQ7kSyRs) this morning) of how remote *repos* are represented, as opposed to just remote *accounts*. I guess that following on from the idea of `https://alice.com/bobert@bobert.com`, Alice could see and interact with Bobert's `foo` repo via something like `https://alice.com/bobert@bobert.com/foo`.

I like PeerTube's remote subscribe UI (a small overlay on the page) much better than Mastodon's annoying pop-up window:

I like PeerTube's remote subscribe UI (a small overlay on the page) *much* better than Mastodon's annoying pop-up window:
Poster
Owner

This is not strictly right; that URI isn't standard and or hard-coded. Each AP software has their own URI. It's advertised over WebFinger as the template property of a link with a rel of http://ostatus.org/schema/1.0/subscribe.

We can pick our own path for this and advertise it via WebFinger.

Yes, strictly speaking we are free to choose any path we want for this, but I just arbitrary chose /authorize_interaction?uri={uri}. The only potential problem this could cause would be if someone had the username authorize_interaction, but I doubt that's going to be a problem.

redirect Alice to https://alice.com/bobert@bobert.com where Bobert's remote account is rendered as I proposed above

This is great for people. What about organisations? Would it be just the same? I guess there's no reason why it shouldn't.

Right, we can use the same process for organizations and repos as well.

We could even include a text box somewhere where users can paste in the URL of a remote user and then are redirected to the /authorize_interaction?uri= endpoint, similar to how in Mastodon, you can paste a URL into the search bar and Mastodon will render the remote AS object.

I would suggest that rather than a new search box, this should work with the existing search box at /explore/repos.

(I'd also argue that that search box should be visible in the global nav bar, not just at that URL, but that's a generic Gitea UI issue rather than being specific to federation.)

Good idea! I also agree that there should be a global search bar, but as you said it's a general UI issue.

There is also the issue (as briefly discussed on Matrix this morning) of how remote repos are represented, as opposed to just remote accounts.

I guess that following on from the idea of https://alice.com/bobert@bobert.com, Alice could see and interact with Bobert's foo repo via something like https://alice.com/bobert@bobert.com/foo.

The challenge with remote repos is that we need some degree of data duplication, but not too much. For instance, if Alice has a repo hello-world on alice.com and Bobert to bobert.com, alice.com shouldn't also store a copy of Bobert's fork since if hello-world is a popular repo, it might be forked thousands of times and alice.com would probably run out of disk space. Even if Bobert sends a federated PR back to Alice, it's better to use AGit instead of actually copying Bobert's repo to alice.com, since large projects with tons of contributors with also eventually run out of disk space.

We will be rendering remote repos, but they'll probably show up as empty on your instance with a text box telling you to go the original instance. This is because our only options for interacting with a remote repo where you don't have a local copy are iframes (terrible idea) or using the Gitea API. It's simpler to just have the user go to the original instance (and that's also what Mastodon does in the image I sent in the first post).

> This is not strictly right; that URI isn't standard and or hard-coded. Each AP software has their own URI. It's advertised over WebFinger as the `template` property of a `link` with a `rel` of `http://ostatus.org/schema/1.0/subscribe`. > > We can pick our own path for this and advertise it via WebFinger. Yes, strictly speaking we are free to choose any path we want for this, but I just arbitrary chose `/authorize_interaction?uri={uri}`. The only potential problem this could cause would be if someone had the username authorize_interaction, but I doubt that's going to be a problem. > > redirect Alice to https://alice.com/bobert@bobert.com where Bobert's remote account is rendered as I proposed above > > This is great for people. What about organisations? Would it be just the same? I guess there's no reason why it shouldn't. Right, we can use the same process for organizations and repos as well. > > We could even include a text box somewhere where users can paste in the URL of a remote user and then are redirected to the /authorize_interaction?uri= endpoint, similar to how in Mastodon, you can paste a URL into the search bar and Mastodon will render the remote AS object. > > I would suggest that rather than a new search box, this should work with the [existing search box at `/explore/repos`](https://codeberg.org/explore/repos). > > (I'd also argue that that search box should be visible in the global nav bar, not just at that URL, but that's a generic Gitea UI issue rather than being specific to federation.) Good idea! I also agree that there should be a global search bar, but as you said it's a general UI issue. > There is also the issue (as briefly [discussed on Matrix](https://matrix.to/#/!SakSkZqjzMsaPCVqlv:matrix.batsense.net/$KoO3t6HauoV3VU97pIAJJD4GUtZAXNqDajpoQ7kSyRs) this morning) of how remote *repos* are represented, as opposed to just remote *accounts*. > > I guess that following on from the idea of `https://alice.com/bobert@bobert.com`, Alice could see and interact with Bobert's `foo` repo via something like `https://alice.com/bobert@bobert.com/foo`. The challenge with remote repos is that we need some degree of data duplication, but not too much. For instance, if Alice has a repo hello-world on alice.com and Bobert to bobert.com, alice.com shouldn't also store a copy of Bobert's fork since if hello-world is a popular repo, it might be forked thousands of times and alice.com would probably run out of disk space. Even if Bobert sends a federated PR back to Alice, it's better to use AGit instead of actually copying Bobert's repo to alice.com, since large projects with tons of contributors with also eventually run out of disk space. We will be rendering remote repos, but they'll probably show up as empty on your instance with a text box telling you to go the original instance. This is because our only options for interacting with a remote repo where you don't have a local copy are iframes (terrible idea) or using the Gitea API. It's simpler to just have the user go to the original instance (and that's also what Mastodon does in the image I sent in the first post).
Sign in to join this conversation.
No Label
No Milestone
No project
No Assignees
2 Participants
Notifications
Due Date

No due date set.

Dependencies

No dependencies set.

Reference: Ta180m/gitea#8
Loading…
There is no content yet.