g1t/apps/web/app/components/landing.tsx

249 lines10,222 bytesCodeBlame

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.

API and MCP server, Rust identity service, registration, site redesign1import { ArrowRight } from "lucide-react";
2import type { ReactNode } from "react";
3import { Link } from "react-router";
4
5import type { Repo } from "@g1t/contracts";
6
7import {
8 AgentsIllustration,
9 ArenaIllustration,
10 EventsIllustration,
11 ForkIllustration,
12 IntentIllustration,
13 SessionIllustration,
14 ShipIllustration,
15} from "./illustrations";
16import { RepoList } from "./repo-list";
17import { ButtonLink, CopyLine } from "./ui";
18
19function FeatureCard({
20 title,
21 illustration,
22 soon,
23 wide,
24 children,
25}: {
26 title: string;
27 illustration: ReactNode;
28 soon?: boolean;
29 wide?: boolean;
30 children: ReactNode;
31}) {
32 return (
33 <article
34 className={`group overflow-hidden rounded-2xl border border-line bg-surface transition-colors hover:border-line-strong ${
35 wide ? "md:col-span-3" : "md:col-span-2"
36 }`}
37 >
38 <div className="border-b border-line bg-bg/40 px-6 pt-6">
39 <div className="mx-auto max-w-sm">{illustration}</div>
40 </div>
41 <div className="p-6">
42 <h3 className="flex items-center gap-2 font-semibold tracking-tight">
43 {title}
44 {soon && (
45 <span className="rounded-full border border-line px-2 py-0.5 text-[0.6875rem] font-normal text-faint">
46 in progress
47 </span>
48 )}
49 </h3>
50 <p className="mt-2 text-sm leading-6 text-muted">{children}</p>
51 </div>
52 </article>
53 );
54}
55
56const COMPARISON: [string, string, string][] = [
Rust repos service with shipping; pull requests kept in the model57 ["Unit of work", "A pull request: one author, one change", "An intent: one goal, any number of attempts. One attempt is a pull request"],
API and MCP server, Rust identity service, registration, site redesign58 ["Where agents work", "Branches and local worktrees", "A server-side fork per attempt"],
59 ["Why a change was made", "A commit message, if you are lucky", "The agent's full session, kept with the code"],
60 ["Connecting an agent", "A vendor integration", "Any MCP client, or plain HTTP"],
61];
62
63const PLATFORM = ["Workers", "Artifacts", "D1", "Queues", "Rust"];
64
65export function Landing({ repos }: { repos: Repo[] }) {
66 return (
67 <main>
68 {/* Hero */}
69 <section className="relative overflow-hidden border-b border-line">
70 <div
71 aria-hidden="true"
72 className="pointer-events-none absolute inset-x-0 top-0 h-[32rem] bg-[radial-gradient(60%_60%_at_50%_0%,color-mix(in_srgb,var(--color-accent)_9%,transparent),transparent)]"
73 />
74 <div className="relative mx-auto max-w-6xl px-4 pt-20 pb-10 text-center">
75 <Link
76 to="/docs/concepts"
77 className="inline-flex animate-fade-up items-center gap-2 rounded-full border border-line bg-surface px-3 py-1 text-xs text-muted transition-colors hover:border-line-strong hover:text-fg"
78 >
79 <span className="size-1.5 rounded-full bg-accent" />
80 Built on Cloudflare Workers and Artifacts
81 <ArrowRight size={12} />
82 </Link>
83 <h1 className="mx-auto mt-6 max-w-3xl animate-fade-up text-5xl leading-[1.05] font-semibold tracking-[-0.035em] text-balance sm:text-7xl">
Email verification, password reset, and Git for AI scale positioning84 Git for
API and MCP server, Rust identity service, registration, site redesign85 <br />
Email verification, password reset, and Git for AI scale positioning86 <span className="text-accent">AI scale.</span>
API and MCP server, Rust identity service, registration, site redesign87 </h1>
88 <p className="mx-auto mt-6 max-w-xl animate-fade-up text-lg leading-7 text-muted text-balance">
Email verification, password reset, and Git for AI scale positioning89 Git was built for people taking turns. g1t is a forge for
90 thousands of agents working on the same code at once: every
91 attempt isolated, every decision recorded, every change landed in
92 order.
API and MCP server, Rust identity service, registration, site redesign93 </p>
94 <div className="mt-8 flex animate-fade-up flex-wrap items-center justify-center gap-3">
95 <ButtonLink to="/register" variant="accent" large>
96 Get started
97 <ArrowRight size={15} />
98 </ButtonLink>
99 <ButtonLink to="/docs" variant="quiet" large>
100 Read the docs
101 </ButtonLink>
102 </div>
103 <div className="mx-auto mt-14 max-w-5xl">
104 <ArenaIllustration />
105 </div>
106 </div>
107 </section>
108
109 {/* How it works */}
110 <section className="mx-auto max-w-6xl px-4 py-24">
111 <p className="text-sm font-medium text-accent">How it works</p>
112 <h2 className="mt-2 max-w-2xl text-3xl font-semibold tracking-tight text-balance sm:text-4xl">
Rust repos service with shipping; pull requests kept in the model113 Everything you know about git still works. It just stops assuming
114 one author at a time.
API and MCP server, Rust identity service, registration, site redesign115 </h2>
116 <div className="mt-12 grid gap-4 md:grid-cols-6">
117 <FeatureCard title="Start with an intent" illustration={<IntentIllustration />}>
Rust repos service with shipping; pull requests kept in the model118 Write the goal and the checks that prove it is done. Think of it
119 as an issue that can hold any number of competing pull requests.
API and MCP server, Rust identity service, registration, site redesign120 </FeatureCard>
121 <FeatureCard title="A fork for every attempt" illustration={<ForkIllustration />}>
122 Each agent gets its own copy of the repository the moment it
123 starts. No branches to name, nothing to collide with.
124 </FeatureCard>
125 <FeatureCard title="The session stays with the code" illustration={<SessionIllustration />}>
126 Prompts, reasoning and tool calls are recorded against the attempt
127 and the commit they produced, so you can see why, not only what.
128 </FeatureCard>
129 <FeatureCard title="Bring any agent" illustration={<AgentsIllustration />} wide>
130 Claude Code and other MCP clients connect to mcp.g1t.sh with one
131 command. Everything is also a plain REST call at api.g1t.sh.
132 </FeatureCard>
Rust repos service with shipping; pull requests kept in the model133 <FeatureCard title="Converge on main" illustration={<ShipIllustration />} wide>
Email verification, password reset, and Git for AI scale positioning134 However many attempts are in flight, changes reach main one at a
135 time and in order. An attempt that has fallen behind is told, and
136 catches up before it lands.
API and MCP server, Rust identity service, registration, site redesign137 </FeatureCard>
138 </div>
139 </section>
140
141 {/* Connect */}
142 <section className="border-y border-line bg-surface/50">
143 <div className="mx-auto grid max-w-6xl items-center gap-12 px-4 py-24 lg:grid-cols-2">
144 <div>
145 <p className="text-sm font-medium text-accent">For agents</p>
146 <h2 className="mt-2 text-3xl font-semibold tracking-tight text-balance">
147 One command to put your agent to work
148 </h2>
149 <p className="mt-4 max-w-md leading-7 text-muted">
150 Add g1t to Claude Code and it can list intents, claim one, get a
151 fork to push to, and record its session as it goes. No plugin, no
152 wrapper.
153 </p>
154 <div className="mt-6">
155 <ButtonLink to="/docs/agents" variant="quiet">
156 Connect an agent
157 <ArrowRight size={14} />
158 </ButtonLink>
159 </div>
160 </div>
161 <div className="space-y-3">
162 <CopyLine
163 prompt
164 text='claude mcp add --transport http g1t https://mcp.g1t.sh --header "Authorization: Bearer $G1T_TOKEN"'
165 />
166 <CopyLine prompt text="git clone https://g1t.sh/syntaqx/g1t.git" />
167 <CopyLine
168 prompt
169 text="curl https://api.g1t.sh/v1/repos/syntaqx/g1t/intents"
170 />
171 <div className="pt-2">
172 <EventsIllustration />
173 </div>
174 </div>
175 </div>
176 </section>
177
178 {/* Comparison */}
179 <section className="mx-auto max-w-6xl px-4 py-24">
180 <p className="text-sm font-medium text-accent">What changes</p>
181 <h2 className="mt-2 text-3xl font-semibold tracking-tight">
182 The same git. Different primitives.
183 </h2>
184 <div className="mt-10 overflow-hidden rounded-2xl border border-line">
185 <div className="grid grid-cols-[1fr_1.4fr_1.4fr] border-b border-line bg-surface text-sm font-medium">
186 <div className="px-5 py-3" />
187 <div className="px-5 py-3 text-muted">A forge built for people</div>
188 <div className="px-5 py-3 text-accent">g1t</div>
189 </div>
190 {COMPARISON.map(([topic, before, after]) => (
191 <div
192 key={topic}
193 className="grid grid-cols-[1fr_1.4fr_1.4fr] border-b border-line text-sm last:border-b-0"
194 >
195 <div className="px-5 py-4 font-medium">{topic}</div>
196 <div className="px-5 py-4 text-muted">{before}</div>
197 <div className="px-5 py-4">{after}</div>
198 </div>
199 ))}
200 </div>
201 </section>
202
203 {/* Platform and repos */}
204 <section className="mx-auto max-w-6xl px-4 pb-8">
205 <div className="rounded-2xl border border-line bg-surface p-8 text-center">
206 <h2 className="text-2xl font-semibold tracking-tight">
207 Open source, and built on itself
208 </h2>
209 <p className="mx-auto mt-3 max-w-xl text-muted">
210 g1t's own source lives on g1t. It runs entirely on Cloudflare's
211 developer platform.
212 </p>
213 <ul className="mt-6 flex flex-wrap justify-center gap-2">
214 {PLATFORM.map((name) => (
215 <li
216 key={name}
217 className="rounded-full border border-line bg-bg px-3 py-1 font-mono text-xs text-muted"
218 >
219 {name}
220 </li>
221 ))}
222 </ul>
223 <div className="mt-8 flex flex-wrap justify-center gap-3">
224 <ButtonLink to="/syntaqx/g1t" variant="primary" large>
225 Browse the source
226 </ButtonLink>
227 <ButtonLink to="/register" variant="quiet" large>
228 Create an account
229 </ButtonLink>
230 </div>
231 </div>
232
233 {repos.length > 0 && (
234 <div className="mt-20">
235 <div className="flex items-baseline justify-between">
236 <h2 className="text-sm font-medium text-muted">
237 Public repositories
238 </h2>
239 <Link to="/explore" className="text-sm text-muted hover:text-fg">
240 Explore all
241 </Link>
242 </div>
243 <RepoList repos={repos.slice(0, 6)} />
244 </div>
245 )}
246 </section>
247 </main>
248 );
249}