Skip to content
90 linesCodeBlameRaw

Pick any line to see why it is the way it is: the commit, the pull request and issue it came from, and what the agent was thinking.

Merge branch 'worktree-agent-aaf03bdceac799c89'1import { useRouteLoaderData } from "react-router";
2
3/**
4 * Where this g1t lives: the site, the REST API, the MCP server and the
5 * social-card service. g1t.sh uses the defaults below; a self-hosted g1t
6 * sets its own (app/lib/addresses.server.ts reads them), and the root
7 * loader hands them to every page.
8 */
9export type Addresses = {
10 /** The site's origin, such as `https://g1t.sh`. Git remotes are under it. */
11 site: string;
12 /** The REST API's origin, which is also the OAuth issuer. */
13 api: string;
14 /** The MCP server's URL, as agents are told to add it. */
15 mcp: string;
16 /** The social-card image service's origin, or null when there is none. */
17 og: string | null;
Repository files and avatars on g1tusercontent.com: raw files, a Raw button, images on file pages and in READMEs18 /**
19 * Where bytes people supplied are served (repository files, avatars), on
20 * an origin of its own that never sees the site's cookies. Self-hosted
21 * without a host of its own, a path on the site (`<site>/-/usercontent`).
22 */
23 usercontent: string;
Merge branch 'worktree-agent-aaf03bdceac799c89'24};
25
26export const HOSTED_ADDRESSES: Addresses = {
27 site: "https://g1t.sh",
28 api: "https://api.g1t.sh",
29 mcp: "https://mcp.g1t.sh",
30 og: "https://og.g1t.sh",
Repository files and avatars on g1tusercontent.com: raw files, a Raw button, images on file pages and in READMEs31 usercontent: "https://g1tusercontent.com",
Merge branch 'worktree-agent-aaf03bdceac799c89'32};
33
34/** The Worker settings the addresses come from; every one optional. */
Repository files and avatars on g1tusercontent.com: raw files, a Raw button, images on file pages and in READMEs35export type AddressSettings = { SITE_URL?: string; API_URL?: string; MCP_URL?: string; OG_URL?: string; USERCONTENT_URL?: string };
Merge branch 'worktree-agent-aaf03bdceac799c89'36
37const trim = (value: string) => value.trim().replace(/\/+$/, "");
38
39/**
40 * The addresses from the Worker's settings. An unset or empty setting is
41 * g1t.sh's address, except `OG_URL`: set to an empty string, it means there
Repository files and avatars on g1tusercontent.com: raw files, a Raw button, images on file pages and in READMEs42 * is no card service, and pages carry no image tags. `USERCONTENT_URL`
43 * unset is g1tusercontent.com on g1t.sh, and a path on the site wherever
44 * `SITE_URL` names another.
Merge branch 'worktree-agent-aaf03bdceac799c89'45 */
46export function addressesFor(settings: AddressSettings): Addresses {
47 const pick = (value: string | undefined, fallback: string) => (value ? trim(value) : "") || fallback;
Repository files and avatars on g1tusercontent.com: raw files, a Raw button, images on file pages and in READMEs48 const site = pick(settings.SITE_URL, HOSTED_ADDRESSES.site);
49 const ownSite = site === HOSTED_ADDRESSES.site;
Merge branch 'worktree-agent-aaf03bdceac799c89'50 return {
Repository files and avatars on g1tusercontent.com: raw files, a Raw button, images on file pages and in READMEs51 site,
52 usercontent: usercontentOf(pick(settings.USERCONTENT_URL, ownSite ? HOSTED_ADDRESSES.usercontent : `${site}/-/usercontent`), site),
Merge branch 'worktree-agent-aaf03bdceac799c89'53 api: pick(settings.API_URL, HOSTED_ADDRESSES.api),
54 mcp: pick(settings.MCP_URL, HOSTED_ADDRESSES.mcp),
55 og: settings.OG_URL === undefined ? HOSTED_ADDRESSES.og : trim(settings.OG_URL) || null,
56 };
57}
58
Repository files and avatars on g1tusercontent.com: raw files, a Raw button, images on file pages and in READMEs59/**
60 * Where uploaded avatars and repository files are served, from the root
61 * loader's data; the site's own paths when it has none (they redirect).
62 */
63export function usercontentFrom(rootData: unknown): string {
64 return (rootData as { addresses?: Addresses } | null | undefined)?.addresses?.usercontent ?? "";
65}
66
67/** The site's own origin is never the usercontent origin: a path on it is. */
68function usercontentOf(address: string, site: string): string {
69 return address === site ? `${site}/-/usercontent` : address;
70}
71
Merge branch 'worktree-agent-aaf03bdceac799c89'72/** The addresses in the root loader's data, or g1t.sh's when it has none. */
73export function addressesFrom(rootData: unknown): Addresses {
74 return (rootData as { addresses?: Addresses } | null | undefined)?.addresses ?? HOSTED_ADDRESSES;
75}
76
77/** This g1t's addresses, from the root loader. */
78export function useAddresses(): Addresses {
79 return addressesFrom(useRouteLoaderData("root"));
80}
81
Code button: the SSH tab shows the address it will have, disabled, with why it is not on yet82/** The SSH clone address of a repository (`git@host:owner/name.git`), from its `owner/name`. */
83export function sshUrl(addresses: Pick<Addresses, "site">, path: string): string {
84 return `git@${new URL(addresses.site).hostname}:${path.replace(/^\/+/, "")}.git`;
85}
86
Merge branch 'worktree-agent-aaf03bdceac799c89'87/** The HTTPS clone address of a repository, from its `owner/name`. */
88export function cloneUrl(addresses: Pick<Addresses, "site">, path: string): string {
89 return `${addresses.site}/${path.replace(/^\/+/, "")}.git`;
90}

This file's history is long; its oldest lines are credited to the oldest commit read.