Files
CC-Manager/server/prisma/migrations/20250117000000_kette_je_nutzer/migration.sql
T
Harlekin 1f4034b397 Jede Liste gehoert einem Spieler, CC-Guthaben wird umgewandelt
Ein Gruppen-CC wird fuer jeden Nutzer einzeln gerechnet: fuer den einen
kann er der gekaufte Platz sein, fuer den anderen ein Redesign seines
vorherigen CCs. Dafuer haengt die Liste jetzt an der Mitgliedschaft
statt am CC, und verschieben ordnet nur die eigene Liste.

Ein Redesign wird nie aus dem CC-Topf bezahlt. Wer sein CC-Guthaben
dafuer einsetzt, wandelt es um: ein Platz weniger, ein bezahltes
Redesign mehr. Damit entfaellt die Ausnahme, die sich bisher durch
Slot-Pruefung und Kettenrechnung zog.

Beim Start werden Buchungen einmalig an die Listen angeglichen.
2026-09-22 12:21:53 +02:00

66 lines
2.6 KiB
SQL

-- Ein Gruppen-CC wird fuer jeden Nutzer einzeln gerechnet: fuer den einen ist
-- er der gekaufte Platz, fuer den anderen ein Redesign seines vorherigen CCs.
-- Deshalb wandert die Liste vom CC an die Mitgliedschaft.
ALTER TABLE "CharacterMember" ADD COLUMN IF NOT EXISTS "lineageId" TEXT;
ALTER TABLE "CharacterMember" ADD COLUMN IF NOT EXISTS "chainPosition" INTEGER NOT NULL DEFAULT 0;
-- Wer den CC angelegt hat, bringt seine bisherige Kette mit.
UPDATE "CharacterMember" m
SET "lineageId" = c."lineageId", "chainPosition" = c."chainPosition"
FROM "Character" c
WHERE c.id = m."characterId" AND c."playerId" = m."playerId" AND m."lineageId" IS NULL;
-- Die uebrigen haengen an einem Eintrag, der schon zugeordnet ist: entweder am
-- CC, den sie dafuer aufgegeben haben, oder an einem frueheren Glied derselben
-- Kette, in der sie mitgezogen wurden. Beides kann mehrere Stufen tief gehen,
-- deshalb die Schleife.
DO $$
DECLARE
ueber_vorgaenger INTEGER;
ueber_kette INTEGER;
geaendert INTEGER := 1;
BEGIN
WHILE geaendert > 0 LOOP
UPDATE "CharacterMember" m
SET "lineageId" = v."lineageId", "chainPosition" = v."chainPosition" + 10
FROM "CharacterMember" v
WHERE v."characterId" = m."predecessorId"
AND v."playerId" = m."playerId"
AND v."lineageId" IS NOT NULL
AND m."lineageId" IS NULL;
GET DIAGNOSTICS ueber_vorgaenger = ROW_COUNT;
UPDATE "CharacterMember" m
SET "lineageId" = q."lineageId",
"chainPosition" = q."chainPosition" + (q."cc_pos" - q."von_pos")
FROM (
SELECT DISTINCT ON (offen.id)
offen.id AS mitglied_id,
v."lineageId",
v."chainPosition",
cm."chainPosition" AS cc_pos,
cv."chainPosition" AS von_pos
FROM "CharacterMember" offen
JOIN "Character" cm ON cm.id = offen."characterId"
JOIN "Character" cv
ON cv."lineageId" = cm."lineageId" AND cv."chainPosition" < cm."chainPosition"
JOIN "CharacterMember" v ON v."characterId" = cv.id AND v."playerId" = offen."playerId"
WHERE offen."lineageId" IS NULL AND v."lineageId" IS NOT NULL
ORDER BY offen.id, cv."chainPosition" DESC
) q
WHERE m.id = q.mitglied_id;
GET DIAGNOSTICS ueber_kette = ROW_COUNT;
geaendert := ueber_vorgaenger + ueber_kette;
END LOOP;
END $$;
-- Alles Uebrige beginnt eine eigene Liste: ein Platz, der fuer sich steht.
UPDATE "CharacterMember"
SET "lineageId" = gen_random_uuid()::text, "chainPosition" = 0
WHERE "lineageId" IS NULL;
ALTER TABLE "CharacterMember" ALTER COLUMN "lineageId" SET NOT NULL;
CREATE INDEX IF NOT EXISTS "CharacterMember_lineageId_idx" ON "CharacterMember"("lineageId");