Skip to content

Protocols: Git and jj

neosource separates the protocol you speak from the engine that stores your repository. The storage engine is not a Git repository on a disk somewhere, and it is not a jj repository either — it is content-addressed objects, an operation log, and operation heads. Protocols are translation at the edge.

The practical consequence: you use whichever client you already use.

Git is fully first-class and is what almost everyone should use. Both transports are implemented:

  • Smart HTTPgit clone, git fetch, git push over HTTPS, using a personal access token for authentication.
  • SSH — the same operations over SSH, using a key you add to your account.

There is no Git subset here and no “compatibility mode”. Ordinary git commands, ordinary remotes, ordinary workflows. See Getting started for the exact URLs and the first push.

If you use jj, you can work against neosource today with jj’s Git interoperability — jj git clone, jj git fetch, jj git push — the same way you would against any Git remote.

This is not incidental. jj drives Git’s protocol v2 through libgit2, which negotiates slightly differently from the git binary; neosource’s protocol edge handles those differences explicitly rather than accidentally. A jj client and a Git client talk to the same endpoints and see the same repository.

What does not exist today is a separate jj-native wire protocol with its own endpoint. jj support means jj clients work, not that there is a second protocol to learn or configure.

Nothing about using neosource requires knowing what jj is. The target user is someone coming from GitHub or GitLab who wants their Git workflow to keep working. jj is an option for people who already want it, not a tax on everyone else.

The engine’s design lineage is jj’s model — that is a fact about how the storage layer was designed, not a requirement placed on you. See The storage engine for what that lineage actually means.

Protocol handlers translate; they do not make correctness decisions. A push arriving over SSH and a push arriving over HTTPS both end up as the same sequence in the engine: authorize, store immutable objects, append an operation record, advance the operation heads. The gateway never advances operation heads itself.

Keeping the edge thin is what makes the engine protocol-agnostic by construction: the rules about what a valid repository state is live in one place, not once per protocol.