pr_01m47d15m3e54sn21z27rpy5n9/services/projects/src/transfer.test.ts

62 lines2,956 bytesCodeBlame
1import { test } from "node:test";
2import assert from "node:assert/strict";
3
4import { moveStatements, slugOf, strandedQuery } from "./transfer.ts";
5
6test("each statement is bound with as many values as it asks for", () => {
7 for (const [stale, current] of [
8 [["syntaqx/g1t"], "flagon-io/g1t"],
9 [["flagon-io/g1t"], "flagon-io/forge"],
10 [["syntaqx/g1t", "flagon-io/g1t"], "flagon-io/forge"],
11 ] as const) {
12 for (const { sql, params } of moveStatements([...stale], current, "rep_1")) {
13 assert.equal(sql.split("?").length - 1, params.length, sql);
14 }
15 }
16 const stranded = strandedQuery(["syntaqx/g1t"], "flagon-io/g1t", "rep_1")!;
17 assert.equal(stranded.sql.split("?").length - 1, stranded.params.length);
18});
19
20test("projects move from the workspace the repository left to the one it is in", () => {
21 const [move] = moveStatements(["syntaqx/g1t"], "flagon-io/g1t", "rep_1");
22 assert.deepEqual(move!.params, ["flagon-io", "flagon-io", "rep_1", "syntaqx"]);
23});
24
25test("a delivery after the rows moved moves nothing but the path", () => {
26 // Transferred back: only the workspace it is not in now moves.
27 const statements = moveStatements(["flagon-io/g1t"], "syntaqx/g1t", "rep_1");
28 assert.equal(statements.filter((s) => s.sql.startsWith("UPDATE OR IGNORE")).length, 1);
29 assert.equal(strandedQuery([], "syntaqx/g1t", "rep_1"), null);
30});
31
32test("a transfer keeps every slug", () => {
33 const statements = moveStatements(["syntaqx/g1t"], "flagon-io/g1t", "rep_1");
34 assert.ok(!statements.some((s) => s.sql.includes("SET slug")));
35 assert.ok(!statements.some((s) => s.sql.includes("SET name")));
36});
37
38test("renamed, the repository's own project takes the new name as its slug if it is free", () => {
39 const statements = moveStatements(["flagon-io/g1t"], "flagon-io/Forge", "rep_1");
40 const slug = statements.find((s) => s.sql.includes("SET slug"))!;
41 assert.match(slug.sql, /^UPDATE OR IGNORE/);
42 assert.match(slug.sql, /is_primary = 1/);
43 assert.deepEqual(slug.params, ["forge", "rep_1", "flagon-io", "g1t"]);
44 const name = statements.find((s) => s.sql.includes("SET name"))!;
45 assert.deepEqual(name.params, ["Forge", "rep_1", "g1t"]);
46 const path = statements.find((s) => s.sql.includes("repo_name"))!;
47 assert.deepEqual(path.params, ["flagon-io", "Forge", "rep_1"]);
48 // Nothing moves between workspaces.
49 assert.equal(statements.filter((s) => s.sql.includes("SET workspace")).length, 0);
50 assert.equal(strandedQuery(["flagon-io/g1t"], "flagon-io/Forge", "rep_1"), null);
51});
52
53test("a rename of letter case alone keeps the slug", () => {
54 const statements = moveStatements(["flagon-io/forge"], "flagon-io/Forge", "rep_1");
55 assert.ok(!statements.some((s) => s.sql.includes("SET slug")));
56 assert.ok(statements.some((s) => s.sql.includes("SET name")));
57});
58
59test("names become slugs as projects spell them", () => {
60 assert.equal(slugOf(" My App! "), "my-app");
61 assert.equal(slugOf("g1t.sh"), "g1t.sh");
62});