import { describe, expect, it } from "vitest"; import { isCompleteGitRemote, parseGitRemoteLocation } from "./git-remote.js"; describe("isCompleteGitRemote", () => { it("treats supported URLs and scp-like addresses as complete remotes", () => { expect(isCompleteGitRemote("https://github.com/owner/repo")).toBe(true); expect(isCompleteGitRemote("http://internal/owner/repo.git")).toBe(true); expect(isCompleteGitRemote("ssh://git@github.com/owner/repo")).toBe(true); expect(isCompleteGitRemote("git@github.com:owner/repo.git")).toBe(true); expect(isCompleteGitRemote(" https://github.com/owner/repo ")).toBe(true); }); it("treats owner/repo shorthand as incomplete (needs a clone protocol)", () => { expect(isCompleteGitRemote("owner/repo")).toBe(false); expect(isCompleteGitRemote("owner/repo.git")).toBe(false); expect(isCompleteGitRemote("")).toBe(false); }); it("rejects schemes the daemon's parser does not accept, so clients agree with the server", () => { // The old client-side regex matched any `scheme://`, classifying these as // complete URLs while the daemon (parseGitRemoteLocation) rejected them — // producing a confusing "use owner/repo format" error. The shared helper // must classify them identically to the daemon. for (const repo of ["git://github.com/owner/repo", "ftp://host/repo", "file:///tmp/repo"]) { expect(isCompleteGitRemote(repo)).toBe(false); expect(parseGitRemoteLocation(repo)).toBeNull(); } }); }); describe("parseGitRemoteLocation port", () => { it("preserves an explicit non-default port from an https remote", () => { expect(parseGitRemoteLocation("https://home-git.example.com:60443/team/repo.git")?.port).toBe( "60443", ); }); it("preserves a port from a plain http remote", () => { expect(parseGitRemoteLocation("http://internal.example.com:3000/team/repo.git")?.port).toBe( "3000", ); }); it("omits the port for a default-port remote", () => { expect(parseGitRemoteLocation("https://github.com/acme/repo.git")?.port).toBeUndefined(); }); it("has no port for an scp-form remote", () => { expect(parseGitRemoteLocation("git@host.example.com:team/repo.git")?.port).toBeUndefined(); }); it("omits an explicitly written default port", () => { expect(parseGitRemoteLocation("ssh://git@github.com:22/acme/repo.git")).toEqual( parseGitRemoteLocation("ssh://git@github.com/acme/repo.git"), ); }); it("reads a scheme remote as a URL rather than scp form", () => { expect(parseGitRemoteLocation("ssh://git@example.com:2222/acme/repo.git")).toEqual({ transport: "ssh", host: "example.com", port: "2222", path: "acme/repo", }); }); });